home *** CD-ROM | disk | FTP | other *** search
/ Software Vault: The Gold Collection / Software Vault - The Gold Collection (American Databankers) (1993).ISO / cdr47 / wasm223.zip / WASM.DOC < prev    next >
Text File  |  1993-05-04  |  200KB  |  5,185 lines

  1.  
  2.  
  3.  
  4.  
  5.  
  6.  
  7.  
  8.  
  9.  
  10.  
  11.  
  12.  
  13.  
  14.  
  15.  
  16.  
  17.                                   \\\ WASM ///
  18.  
  19.                                Wolfware Assembler
  20.                                   Version 2.11
  21.  
  22.                                   User's Manual
  23.  
  24.  
  25.                         (C) Copyright 1987 by Eric Tauck
  26.                                All rights reserved
  27.  
  28.  
  29.  
  30.  
  31.                                 Table of Contents
  32.  
  33.              Distribution Policy ................................ 1
  34.              Introduction ....................................... 2
  35.              Assembling Programs ................................ 4
  36.              Basic Syntax ....................................... 6
  37.                Symbols .......................................... 8
  38.                Instructions ..................................... 9
  39.                Operands ........................................ 10
  40.                Operand Expressions ............................. 14
  41.              Program Structure ................................. 16
  42.              Procedures ........................................ 17
  43.              Conditional Assembly .............................. 18
  44.                Conditional Directives .......................... 19
  45.                Nested Conditional Assembly ..................... 22
  46.                Conditional Operators ........................... 24
  47.                Conditional Operand Testing ..................... 25
  48.              Macros ............................................ 27
  49.                Defining Macros ................................. 28
  50.                Invoking Macros ................................. 30
  51.                Nested Macros ................................... 32
  52.                Conditional Macros .............................. 33
  53.                Listing of Macros ............................... 34
  54.              Data .............................................. 35
  55.              Assembly Directives ............................... 37
  56.              Functional Operands ............................... 55
  57.              Assembly Constants ................................ 61
  58.              Reserved Symbols .................................. 65
  59.              Assembly Listing .................................. 66
  60.              Symbol Table Listing .............................. 68
  61.              Assembly Messages ................................. 69
  62.              Instruction Set ................................... 80
  63.              8087 Programming .................................. 97
  64.              External Subroutines .............................. 98
  65.              Source Code Clarification ......................... 99
  66.              Memory Limitations ............................... 103
  67.              Bibliography ..................................... 104
  68.              Index ............................................ 105
  69.  
  70.  
  71.        Distribution Policy                                              1
  72.  
  73.                                Distribution Policy
  74.  
  75.        Unmodified copies of WASM may be shared and distributed.  WASM may
  76.        be used without obligation to me, the author.  The most current
  77.        version of WASM may be acquired on double sided / double density 5
  78.        1/4" diskettes by sending $10 (checks payable to Eric Tauck) to
  79.        the address below.
  80.  
  81.          Eric Tauck
  82.          1304 Deerpass Road
  83.          Marengo, IL  60152
  84.  
  85.        I can also be reached electronically at:
  86.  
  87.          CompuServe .... 72457,1557
  88.  
  89.                              DISCLAIMER OF WARRANTY
  90.  
  91.        THIS SOFTWARE AND MANUAL ARE DISTRIBUTED "AS IS" AND WITHOUT
  92.        WARRANTIES AS TO PERFORMANCE OF MERCHANTABILITY OR ANY OTHER
  93.        WARRANTIES WHETHER EXPRESSED OR IMPLIED.  BECAUSE OF THE VARIOUS
  94.        HARDWARE AND SOFTWARE ENVIRONMENTS INTO WHICH THIS PROGRAM MAY BE
  95.        PUT, NO WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE IS OFFERED.
  96.  
  97.        GOOD DATA PROCESSING PROCEDURE DICTATES THAT ANY PROGRAM BE
  98.        THOROUGHLY TESTED WITH NON-CRITICAL DATA BEFORE RELYING ON IT.
  99.        THE USER MUST ASSUME THE ENTIRE RISK OF USING THE PROGRAM.  ANY
  100.        LIABILITY OF THE SELLER WILL BE LIMITED EXCLUSIVELY TO PRODUCT
  101.        REPLACEMENT OR REFUND OF PURCHASE PRICE.
  102.  
  103.  
  104.        2                                                     Introduction
  105.  
  106.                                   Introduction
  107.  
  108.        Wolfware Assembler (WASM) is an assembler for the 8086 and related
  109.        microprocessors.  It takes a standard ASCII text file of
  110.        instruction mnemonics for input and produces an executable COM
  111.        file and an optional list file for output.
  112.  
  113.        - Minimum system requirements: an IBM PC or compatible computer,
  114.          MS/PC DOS 2.00 or up, and about 100 kilobytes of free memory.
  115.  
  116.        - Features: supports full range of 8086 and 8087 instructions and
  117.          addressing, most standard assembly directives, signed and
  118.          unsigned numbers, operand expressions, conditional assembly,
  119.          macros, produces executable code (does not require linking), and
  120.          fairly fast operation.
  121.  
  122.        - Limitations: relocatable object (.OBJ) modules are not
  123.          supported, floating point numbers cannot be initialized, and the
  124.          source code is not MASM compatible.
  125.  
  126.        Assembly language is a programming language in which the source
  127.        statements are translated directly into individual microprocessor
  128.        instructions.  This direct translation allows complete control
  129.        over the computer and the greatest possible optimization of a
  130.        program.  Programming in assembly language has immediate and
  131.        practical benefits:
  132.  
  133.        - Programs can be made to run hundreds, maybe thousands of times
  134.          faster than their high level language counterparts.
  135.  
  136.        - Programs are usually much smaller and more efficient.
  137.  
  138.        - Programs can take full advantage of the system it is meant to
  139.          run on.
  140.  
  141.        Assembly language is essential where speed, compactness, and low
  142.        level or hardware control are the primary requirements.  WASM is
  143.        best suited for writing smaller, stand-alone programs and
  144.        optimized routines that are used by other programs.  WASM is ideal
  145.        for writing machine language subroutines for BASIC or Turbo
  146.        Pascal.
  147.  
  148.        The disadvantage of assembly language is that the writing and
  149.        debugging of such programs are often more difficult.  Another
  150.        consideration is that assembly language is not very portable, i.e.
  151.        programs written in assembly language are usually restricted to
  152.        one type of computer.
  153.  
  154.        WASM is easier to use than most commercial assemblers because of
  155.        its simplified syntax and program structure.  Of course, by the
  156.        same token, WASM is not necessarily compatible with other
  157.        assemblers.
  158.  
  159.  
  160.        Introduction                                                     3
  161.  
  162.        Though this documentation explains some of the basic concepts of
  163.        assembly language, no attempt is made to to teach it.  The user
  164.        should be familiar with the basic concepts of programming and have
  165.        a general knowledge of the the 8086 microprocessor.  See the
  166.        bibliography for some possible reference materials.
  167.  
  168.  
  169.        4                                              Assembling Programs
  170.  
  171.                                Assembling Programs
  172.  
  173.        Programs are assembled by running the assembler and specifying the
  174.        names of the source, object, and list files.  To run the assembler
  175.        from any DOS prompt, you type "WASM" and then a carriage return.
  176.        A brief opening message will be displayed and you will be prompted
  177.        for all the required information.  Default file names will be
  178.        provided if no name is otherwise specified.  The default name
  179.        appears in brackets at the end of the prompt line.  An entire file
  180.        name consists of a path, filename, and extension.  The drive
  181.        specification is considered part of the path.
  182.  
  183.        The source file contains the list of instructions that are to be
  184.        assembled into machine code.  It must be a standard ASCII text
  185.        file created by the user before assembly.  If you enter a source
  186.        file name without an extension, the default extension of ASM will
  187.        be automatically added to it.  ASM is the standard filename
  188.        extension for assembler source files.
  189.  
  190.        The object file contains the machine code result of the assembly.
  191.        The object file will be created if it doesn't already exist; if
  192.        does exist the original file will be overwritten.  The default
  193.        name is the source path and filename with an extension COM.  You
  194.        may enter any component(s) of the name which you want to be
  195.        different from the default name (like only the path and extension
  196.        for instance).  COM is reserved by DOS as the filename extension
  197.        for executable "command" files.  The object file is not a linkable
  198.        object file, but a binary image of the compilation.  The object
  199.        file, assuming the source code was logically correct and that
  200.        there were no errors during assembly, is directly executable from
  201.        DOS.  If you use the extension COM, you can run the assembled
  202.        program just by typing its filename.
  203.  
  204.        The list file contains the listing of the assembly.  The list file
  205.        will be created if it doesn't already exist; if does exist the
  206.        original file will be overwritten.  If no list file is specified,
  207.        no listing will be produced. If you do enter a filename, the
  208.        object path and an extension of LST will be used as the default.
  209.        Specifying CON as the list file will send the listing to the
  210.        screen, and specifying PRN as the list file will send the listing
  211.        to the printer.  The listing itself is more thoroughly described
  212.        under Assembly Listing.
  213.  
  214.        The names of the three files may be entered on the command line
  215.        when WASM is initially executed.  To do this you must provide at
  216.        least the name of the source file.  The other two names are
  217.        optional.  All names should be separated from each other by a
  218.        comma.  You can use a default name by placing a comma without a
  219.        name, or by just leaving the name off the end.  The normal
  220.        defaults to all names still apply.
  221.  
  222.  
  223.        Assembling Programs                                              5
  224.  
  225.        Examples of command line file specifications:
  226.  
  227.          WASM TEST
  228.            source is TEST.ASM, object is TEST.COM, and there is no list
  229.  
  230.          WASM ABC, , ABC
  231.            source is ABC.ASM, object is ABC.COM, and list is ABC.LST
  232.  
  233.          WASM  SUBRT, .BLD
  234.            source is SUBRT.ASM, object is SUBRT.BLD, and there is no list
  235.  
  236.          WASM TEST.TXT, STUPID.BIN, HELLO.DOC
  237.            source is TEST.TXT, object is STUPID.BIN, and list is
  238.            HELLO.DOC
  239.  
  240.          WASM A:\ASSM\PROG1,,B:PROG1
  241.            source is A:\ASSM\PROG1.ASM, object is A:\ASSM\PROG1.COM, and
  242.            the list is B:PROG1.LST
  243.  
  244.          WASM GAME.SRC, C:\GAMES\.COD, C:\LISTS\GAME
  245.            source is GAME.SRC, object is C:\GAMES\GAME.COD, and the list
  246.            is C:\LISTS\GAME.LST
  247.  
  248.        If there are errors detected during assembly, they will be
  249.        displayed in the listing.  If there is no listing being generated,
  250.        the errors will be displayed to the screen along with the line
  251.        causing the error.  Any errors should be corrected and the program
  252.        reassembled before running or debugging the program.
  253.  
  254.        At the end of assembly several statistics are displayed: the
  255.        number of errors, the number of lines assembled, the number of
  256.        bytes of code, and the number of symbols defined.  These
  257.        statistics are sent to the list file if a listing is being
  258.        generated, otherwise they will be displayed to the screen.  A
  259.        message stating if any errors where detected will shown if the
  260.        assembly statistics were not displayed to the screen.
  261.  
  262.        An error code is returned upon termination.  This error code can
  263.        be acted upon in a batch file with ERRORLEVEL (see your DOS manual
  264.        for details).  The error codes are as follows:
  265.  
  266.         Code  Meaning
  267.         ----  -------
  268.          0    no lines flagged
  269.          1    lines were flagged for comment but no errors were detected
  270.          2    errors were detected but the assembly was completed
  271.          3    the assembly was prematurely terminated due to errors
  272.          4    assembly could not begin (incorrect DOS or not enough mem.)
  273.  
  274.  
  275.        6                                                     Basic Syntax
  276.  
  277.                                   Basic Syntax
  278.  
  279.        The source file must be a standard ASCII text file.  The only
  280.        control characters given special treatment are line boundaries
  281.        (ASCII codes 13 and 10) and end of file markers (ASCII code 26).
  282.        All other control characters are treated as spaces.  The source
  283.        lines may be up to 160 characters long.  If the source file does
  284.        not have an end of file marker, the assembler will read the number
  285.        of bytes recorded in the directory. The line editor EDLIN.COM
  286.        provided with DOS is suitable for creating source files.
  287.  
  288.        All 8086 instructions perform an operation on zero, one, or two
  289.        operands.  Assembly directives (commands to control the assembler
  290.        itself) are implemented in a similar manner.  Generally each line
  291.        will contain a single 8086 instruction, or directive, and its
  292.        operands.  In addition to instructions and their operands, a line
  293.        may contain a symbol declaration.
  294.  
  295.        The source file is assembled line by line.  Each line is divided
  296.        up into fields separated by delimiters.  Delimiters consist of
  297.        spaces and most control characters.  How the assembler tries to
  298.        interpret each field is based on the location of the field within
  299.        the line.  Lines are interpreted according to the following
  300.        format:
  301.  
  302.                    Symbol    Instruction  Operands    ;Comment
  303.  
  304.        Symbols must begin on the first character of the line.  If the
  305.        first character of a line is a delimiter, the line is assumed not
  306.        to contain a symbol declaration.  Symbols are only required when
  307.        the instruction is one that specifically defines some sort of
  308.        symbol (like an equate or macro declaration).  Symbols may be any
  309.        length as long as they fit on the line.  Symbols may consist of
  310.        most characters as long as they are unique from each other and all
  311.        predefined symbols.  The rule of thumb is to start symbols with a
  312.        letter and make the rest of the symbol out of numbers, letters,
  313.        and underscores.  Restrictions on symbol declarations are more
  314.        thoroughly described under Reserved Symbols.  Symbols in general
  315.        are described under Symbols.
  316.  
  317.        Instructions must be separated by at least one delimiter from the
  318.        symbol.  If there is no symbol, at least one delimiter must
  319.        precede the instruction (so it doesn't start on the first
  320.        character of the line).  All instructions are predefined.  See
  321.        Instructions.
  322.  
  323.        Operands must be separated by at least one delimiter from the
  324.        instruction.  Since a single operand may consist of multiple
  325.        fields, operands must be separated from each other by commas.  The
  326.        instruction determines how many of what kind of operands are
  327.        required.  See Operands.
  328.  
  329.  
  330.        Basic Syntax                                                     7
  331.  
  332.        Comments come at the end of the line after a semi-colon.  Comments
  333.        may consist of anything and be any length as long as they fit on
  334.        the line.  Comments are always optional and are only there to
  335.        assist the programmer in understanding the source code.
  336.  
  337.        Blank lines may be placed in the source code to improve
  338.        readability.  Blank lines are ignored by the assembler.  Lines may
  339.        also contain only a comment, in which case they are treated as
  340.        blank lines.
  341.  
  342.  
  343.        8                                                          Symbols
  344.  
  345.                                      Symbols
  346.  
  347.        Symbols are used to identify certain aspects of the source
  348.        program.  Symbols allow those aspects to be referenced
  349.        symbolically.  The effective use of symbols can make a program
  350.        easier to understand.  Symbols can also simplify the modification
  351.        of a program.  By changing the portion of the program represented
  352.        by the symbol, you automatically change the program at every
  353.        location the symbol is used.
  354.  
  355.        A symbol is created by declaring it.  This is done by placing the
  356.        symbol field on the first column of a source line.  A line may
  357.        contain only a symbol or a symbol and an instruction.  Declaring a
  358.        symbol causes the assembler to internally store it in the symbol
  359.        table.  An ambiguity arises if a particular field is defined more
  360.        than once as a symbol, since if that symbol is used, the assembler
  361.        will not be able to tell which definition is actually being
  362.        accessed.  For this reason, all symbols must be unique from each
  363.        other.  In addition to being unique from each other, programmer
  364.        defined symbols must be unique from all predefined symbols.
  365.        Restrictions on symbol declarations are more thoroughly described
  366.        under Reserved Symbols.
  367.  
  368.        Symbols come in several different types, the most common of which
  369.        is the label.  Labels identify a location in memory.  Labels are
  370.        used for two purposes, branching and data access.  Labels for
  371.        branching are called near labels.  Labels for data access are
  372.        called memory labels.  Memory labels come in different sizes
  373.        according to how many bits of memory are referenced.  The other
  374.        symbol types are equates and macros.  Equates represent a single
  375.        number.  Macros represent an entire series of instructions.
  376.  
  377.        The symbol type is determined by the instruction.  The declaration
  378.        directives (DB, DW, and DS) create memory labels, the EQU
  379.        directive creates an equate, the MACRO directive creates a macro,
  380.        and the LABEL directive creates a label of a specified type.  Most
  381.        other instructions, and symbols on lines without instructions,
  382.        result in near labels.
  383.  
  384.        Symbols are used by the program in two different ways, as
  385.        instructions and as operands.  Only macros are used as
  386.        instructions.  The remaining symbol types are used as operands.  A
  387.        symbol does not have to be declared before it is used, i.e. memory
  388.        references, equates, and macros may be declared anywhere in the
  389.        program.  Near labels should be placed at the location where the
  390.        code execution should continue after the branch.
  391.  
  392.  
  393.        Instructions                                                     9
  394.  
  395.                                   Instructions
  396.  
  397.        An 8086 instruction specifies the action that should be carried
  398.        out on the operands by the microprocessor.  Assembly directives
  399.        are special instructions to control the assembly itself.  8086
  400.        instructions and directives are implemented in the same manner,
  401.        there is no syntactic difference between the two.
  402.  
  403.        Over a hundred different instructions are recognized by the 8086
  404.        microprocessor.  The two major types of instructions are those
  405.        that manipulate bits in memory and those that transfer control
  406.        from one location in the program to another.  A summary of all the
  407.        legal instructions can be found under Instruction Set. For a full
  408.        explanation of all 8086 instructions, you should acquire a book on
  409.        the subject.
  410.  
  411.        There are assembly directives for many different purposes.
  412.        Specific assembly directives are described in their relevant
  413.        sections and under Assembly Directives.
  414.  
  415.  
  416.        10                                                        Operands
  417.  
  418.                                     Operands
  419.  
  420.        The operands describe what is being acted upon by the instruction.
  421.        There are many different types of operands.  The number and type
  422.        of operands required is determined by the particular instruction.
  423.        The operands needed for an instruction can be looked up under
  424.        Instruction Set.  WASM figures out the type of an operand by
  425.        looking at it and trying to match it to one of the formats it
  426.        recognizes.  If the operand is not recognized as a standard
  427.        predefined type, the symbol table is searched to see if has been
  428.        defined by the programmer.
  429.  
  430.        The following is a list of the legal operand types and their
  431.        formats:
  432.  
  433.          I. Immediate data operands.
  434.  
  435.             A. Numbers with an optional plus or minus preceding it.  All
  436.                numbers must begin with a 0 to 9, and anything that begins
  437.                as such is considered a number.  Numbers with a sign must
  438.                be in the range -32768 to +32767, otherwise they must be 0
  439.                to 65535
  440.  
  441.                1. A binary number of up to 16 digits of ones and zeros
  442.                   followed by a "B".
  443.  
  444.                2. A decimal number from 0 to 65535.
  445.  
  446.                3. A hexadecimal number of up to 4 digits of 0 to F
  447.                   followed by an "H".  Hexadecimal numbers that begin
  448.                   with A to F should have a preceding 0.
  449.  
  450.             B. A character enclosed in single quotes.  The character is
  451.                converted to an 8 bit ASCII value, so 'z' would be the
  452.                same as the number 122.
  453.  
  454.             C. A pair of characters enclosed in single quotes.  The
  455.                characters are converted to a 16 bit value calculated from
  456.                their ASCII values.  If 'ab' where moved into a register,
  457.                the high byte would receive the value of 'b' and the low
  458.                byte would receive the value of 'a'.  'ab' is the same as
  459.                the number (98*256)+97 = 25185 or 6261H.  The values of
  460.                'a' and 'b' are backwards because of the way the 8086
  461.                stores 16 bit numbers.
  462.  
  463.             D. Assembly constants.  These are special symbols that return
  464.                a value set by the assembler.  See Assembly Constants.
  465.  
  466.         II. Register operands.
  467.  
  468.             A. One of the following 8 bit registers:
  469.  
  470.                 AH  AL  BH  BL  CH  CL  DH  DL
  471.  
  472.  
  473.        Operands                                                        11
  474.  
  475.             B. One of the following 16 bit registers:
  476.  
  477.                 AX  BX  CX  DX  SP  BP  SI  DI
  478.  
  479.             C. One of the following segment registers:
  480.  
  481.                 CS  SS  DS  ES
  482.  
  483.        III. Memory operands.
  484.  
  485.             A. Direct addressing with a value enclosed by brackets.  All
  486.                numbers (immediate data) inside the brackets are added or
  487.                subtracted together to form the value.
  488.  
  489.             B. Indirect addressing through the use of one of the
  490.                following register combinations with an optional value
  491.                added or subtracted in:
  492.  
  493.                 BX  BP  DI  SI
  494.  
  495.                 BX+DI  BX+SI  BP+DI  BP+SI
  496.  
  497.                All the addressing components should be surrounded by
  498.                brackets.  The registers can appear in any order and may
  499.                be mixed up with any numbers.  All numbers (immediate
  500.                data) are added or subtracted together to form the value.
  501.                The OFFSET function is assumed for any labels (i.e. OFFSET
  502.                can be left out).
  503.  
  504.         IV. A string of any sequence of characters surrounded by single
  505.             quotes.  Note: single quotes cannot be represented as a
  506.             character in a string or as an immediate data character, it
  507.             can only be represented as a numerical value.
  508.  
  509.          V. A single question mark.  This means the the programmer
  510.             doesn't know or care what the operand is.  A question mark is
  511.             interpreted as a zero.
  512.  
  513.         VI. Certain symbols types are used as operands, including equates
  514.             and labels.  See Symbols.
  515.  
  516.        VII. Functional operands may be used to modify or isolate specific
  517.             aspects of of other operands.  See Functional Operands.
  518.  
  519.        VIII. An 8087 stack operand.  These operands reference the 8087
  520.              stack relative to the stack top in the form ST(i), where
  521.              i is a displacement 0 to 7.  The stack top, ST(0), can also
  522.              be specified as just ST.
  523.  
  524.        Operands always have a size associated with them (measured in
  525.        bits).  If the instruction is one that transfers data from one
  526.        operand to another, the sizes of the operands for the instruction
  527.        must agree.
  528.  
  529.  
  530.        12                                                        Operands
  531.  
  532.        The size of immediate data is the number bits it represents.
  533.        Usually 8 bits of immediate data is compatible with 16 bits (i.e
  534.        WASM is smart enough to extend 8 bits of data into 16 bits).
  535.  
  536.        Immediate data sizes:
  537.  
  538.          Immediate Data                 Size in Bits
  539.          --------------                 ------------
  540.          unsigned number 0 to 255         8 or 16
  541.          signed number -128 to 127        8 or 16
  542.          character in quotes              8 or 16
  543.          unsigned number 0 to 65535       16
  544.          signed number -32728 to 32727    16
  545.          double character in quotes       16
  546.  
  547.        The size of register and memory operands are the number of bits
  548.        that can be moved in and out of them.  The size of registers are
  549.        predefined.  The size of memory operands must be defined in the
  550.        declaration or with a functional operand that sets the size.  If a
  551.        memory operand is being operating upon with a register, the memory
  552.        operand is assumed to be the same size as the register.
  553.  
  554.        Examples of operands:
  555.  
  556.          ;*** Immediate Data ***
  557.  
  558.           Mov Dh, -100
  559.           Mov Bl, 00101001b
  560.           Mov Al,'W'     ;move the ASCII value of upper-case w to AL
  561.  
  562.           Mov Ax,', '    ;move a comma and space into AX,
  563.           Stosw          ;it is stored in the same order (comma first)
  564.  
  565.          ;remember that numbers MUST start with 0 to 9, even
  566.          ;hexadecimal numbers
  567.           Mov Ax,0ffffh  ;move ffff hex to AX
  568.  
  569.          ;*** Registers ***
  570.  
  571.          ;8 bit examples
  572.           Mov AL,DL
  573.           Mov CL,0
  574.  
  575.          ;16 bit examples
  576.           Mov Ax,Dx
  577.           Mov Cx,0
  578.  
  579.          ;segment examples
  580.           Mov Dx,Ss
  581.           Mov Cx,0   ;
  582.           Mov Es,Cx  ;cannot move immed. directly to seg
  583.  
  584.  
  585.        Operands                                                        13
  586.  
  587.          ;*** Memory operands ***
  588.  
  589.          ;direct reference examples
  590.           Mov [100],Ax           ;size is the same as AX
  591.           Mov Byte [100], 0      ;size is set with BYTE
  592.           Push Data              ;DATA is defined below, not ambiguous
  593.           Mov Data,0
  594.  
  595.          ;the next three produce the same effect
  596.           Mov CX,[Data]          ;OFFSET implied
  597.           Mov CX,[Offset Data]
  598.           Mov CX,Data            ;this is best
  599.  
  600.          ;indirect reference examples
  601.           Mov [Bx],Ax
  602.           Mov Dx,[Bx+Si+100]
  603.           Inc Byte [Offset Data+Di-1001011b+Bp-3]
  604.           Mov Cx, [Data+Bx]      ;BX acts as an index into DATA
  605.  
  606.          Data Dw  ?
  607.  
  608.          ;*** Near labels ***
  609.  
  610.          Label1                  ;no code, points to NOP
  611.          Lable2  Label   Near    ;explicit label declaration, no code
  612.          Label3  Nop             ;points to its own instruction
  613.          ;
  614.          ;all three of these jump to the NOP instruction above
  615.           Jmps Label1
  616.           Jmps Label2
  617.           Jmps Label3
  618.  
  619.          ;*** Strings ***
  620.  
  621.           Db 'this is a string'
  622.           Db 'it',39,'s cold'    ;this declares the string "it's cold"
  623.  
  624.          ;*** 8087 stack ***
  625.  
  626.           Fild ST, Word [Bx]
  627.           Fmul ST(5), ST(0)
  628.  
  629.  
  630.        14                                             Operand Expressions
  631.  
  632.                                Operand Expressions
  633.  
  634.        Immediate data operands may be combined into expressions.  Any
  635.        number of operands may be combined sequentially.  Parenthesis may
  636.        also be used within expressions to control the order of
  637.        evaluation.  Parenthesis can be nested approximately ten deep.  A
  638.        sign may come before parenthesis, but the range of the value
  639.        within the parenthesis is not checked.  All operand expressions
  640.        are evaluated during assembly.
  641.  
  642.        Near and memory labels may also be modified via expressions.  Any
  643.        immediate data operands may be combined with a near or memory
  644.        label.  Adding or subtracting a value to or from a label has the
  645.        effect of an additional displacement.  The label must be the first
  646.        component of the expression.
  647.  
  648.        The legal operators for combining operands are:
  649.  
  650.          Operator  Function
  651.          --------  --------
  652.             +      addition        <--)  Arithmetic
  653.             -      subtraction        )
  654.             *      multiplication     )
  655.             /      division           )
  656.             \      remainder          )
  657.             MOD    remainder       <--)
  658.             AND    and             <----)  Logic
  659.             OR     or                   )
  660.             XOR    xor             <----)
  661.             =      equals          <------)  Conditional
  662.             <      less than              )
  663.             >      greater than    <------)
  664.  
  665.        The use of conditional operators are described under Conditional
  666.        Operators, the other operators carry out the specified standard
  667.        arithmetic and logic operations.  If some sort of error occurs
  668.        with AND, OR, XOR, or MOD, instead of displaying the literal
  669.        operator, only the first letter A, O, X, or \ for MOD will be
  670.        displayed.
  671.  
  672.        Examples of operand expressions:
  673.  
  674.          ;the following lines all assemble to "move zero to AX"
  675.           Mov Ax,0
  676.           Mov Ax,-21 + ((20 Mod 19)+ 20)
  677.           Mov Ax,-21 - -21
  678.           Mov Ax,50000 * (10\10)
  679.           Mov Ax,-6 / -3 - 2
  680.           Mov Ax,Not (1111111111111110b Or (0feh Xor (65535 And 1)))
  681.           Mov Ax,0ffh-128-64-32-16-8-4-2-1
  682.  
  683.  
  684.        Operand Expressions                                             15
  685.  
  686.          ;here is how to load a double word
  687.          ;of storage a word at a time
  688.           Mov Word Location, Offset Routine   ;load first word
  689.           Mov Ax, Ds
  690.           Mov Word Location + 2, Ax           ;load second word
  691.  
  692.          Location Label Dword
  693.           Ds 4
  694.  
  695.        16                                               Program Structure
  696.  
  697.                                 Program Structure
  698.  
  699.        Though programs may be organized in any fashion, it is usually a
  700.        good idea to make them "structured."  Structured programs are
  701.        generally easier to understand and modify.  Because of their
  702.        inherently straightforward design, structured programs are less
  703.        likely to contain errors and usually accomplish the task with a
  704.        minimum of code.
  705.  
  706.        Structured programming divides a program into separate routines,
  707.        each of which is treated like a separate program.  Every routine
  708.        encompasses a single or group of functions that make up the total
  709.        operation of the program.  Direct transfer of control from one
  710.        routine to another is not allowed.  Direct communication between
  711.        routines is also not allowed.  A routine may call another routine,
  712.        but when the other routine is finished, control must be returned
  713.        to the caller.  Information should only be passed from a routine
  714.        to its subroutine by parameters or by data that is explicitly
  715.        intended as global.
  716.  
  717.        Assembly language doesn't naturally lend itself to structured
  718.        programming the way a high-level language like Pascal does.  There
  719.        is nothing to prevent the programmer from entering a routine and
  720.        then jumping directly to another routine.  WASM provides two
  721.        methods to assist in creating a structured program: procedures and
  722.        macros.  The implementation for procedures and macros are
  723.        described under Procedures and Macros, respectively.
  724.  
  725.  
  726.        Procedures                                                      17
  727.  
  728.                                    Procedures
  729.  
  730.        A procedure is a type of programmer defined routine.  A procedure
  731.        is accessed with the 8086 CALL instruction.  Only one copy of a
  732.        procedure exists, unlike macros, which, in the process of
  733.        assembly, create a copy of their routine every time they are
  734.        invoked.  The use of procedures makes a program shorter but
  735.        slower.  Lengthy routines should always be declared as procedures,
  736.        especially if they are called in many different places.
  737.        Parameters are passed to procedures through registers or by
  738.        placing the data on the stack.
  739.  
  740.        Procedures are implemented by the PROC and ENDP directives.  PROC
  741.        starts a procedure.  Its operand is either NEAR, for routines in
  742.        the same segment, or FAR, for routines that may be in another
  743.        segment.  All procedures that are called from within the program
  744.        should be NEAR.  FAR should be used by procedures that will be
  745.        called externally from another program, like a machine language
  746.        BASIC subroutine, or for routines that are called indirectly, like
  747.        an interrupt handler.  A symbol may be declared along with the
  748.        PROC directive.  This symbol becomes the label that identifies the
  749.        procedure and is used when calling it.  ENDP finishes a procedure.
  750.        It has no operands.
  751.  
  752.        The last executed 8086 instruction in a procedure should be a RET.
  753.        This instruction will return control to the code that called the
  754.        routine in the first place.
  755.  
  756.        Procedures may be nested up to ten deep.  The nest number of a
  757.        procedure is displayed in the listing, see Assembly Listing.
  758.        Nesting a procedure doesn't really make it local, as is implied,
  759.        though it still should be treated as if it were.  Procedures
  760.        should not be called outside of the procedure that they were
  761.        declared in.  Also data declared inside of a procedure should not
  762.        be accessed outside of it.
  763.  
  764.        Procedural declarations create object code.  This means that the
  765.        program must either jump around them or the declarations must be
  766.        placed somewhere out of the way, like at the end of the program.
  767.  
  768.          ;small example of program structure and
  769.          ;syntax using procedures
  770.  
  771.             :            ;main program
  772.           Call Subrt     ;transfer control to the subroutine
  773.             :            ;main program
  774.  
  775.          Subrt Proc Near ;start of subroutine declaration
  776.             :            ;subroutine code
  777.           Ret            ;returns control to main program
  778.           Endp           ;end of subroutine declaration
  779.  
  780.  
  781.        18                                            Conditional Assembly
  782.  
  783.                               Conditional Assembly
  784.  
  785.        Conditional assembly is to assemble or skip certain defined parts
  786.        of the source code based on programmer defined conditions.
  787.        Conditional assembly may be used anywhere within a program, to
  788.        enable or disable any sections of source code.  Source code that
  789.        is disabled (skipped) has no effect upon the assembly.
  790.  
  791.        Conditional assembly is probably most useful in macros, where the
  792.        programmer may want a macro to assemble in a certain way based
  793.        upon its parameters.
  794.  
  795.        Conditional assembly is controlled by special conditional
  796.        directives. These directives themselves never show up in the
  797.        listing.
  798.  
  799.  
  800.        Conditional Directives                                          19
  801.  
  802.                              Conditional Directives
  803.  
  804.        Conditional assembly is controlled by the IF, IFN, NEXTIF, ELSEIF,
  805.        ELSE, and ENDIF directives.  All conditional sections of code must
  806.        start with an IF or IFN and end with an ENDIF.  The other
  807.        directives, NEXTIF, ELSEIF, and ELSE, may optionally be used in
  808.        the middle.
  809.  
  810.        The IF directive starts a conditional section of code.  The IF
  811.        directive can be thought of as "if the condition is true, then
  812.        assemble the following code."  The "condition" for conditional
  813.        directives is a single immediate data operand.  The operand is
  814.        true if its value is not equal to zero, false if its value is
  815.        equal to zero.  If the condition is false, all the source code
  816.        after the IF is skipped up until a matching ENDIF or another
  817.        conditional statement is reached.
  818.  
  819.          ;IF is true, MOV AX,1 is assembled
  820.           If 9283    ;value not equal to zero, true
  821.            Mov Ax,1
  822.           Endif
  823.  
  824.          ;IF is false, ADD DX,CX is not assembled
  825.           If 0       ;value equal to zero, false
  826.            Add Dx,Cx
  827.           Endif
  828.  
  829.        The IFN directive works just like an IF directive except that the
  830.        condition is reversed.  IFN can be thought of as "if the condition
  831.        is not true then assemble the following code."  IFN starts a
  832.        section of conditional code, just like IF.
  833.  
  834.          ;the IFN condition is false, so the
  835.          ;MOV AX,1 is assembled
  836.           Ifn 0      ;value is zero, false
  837.            Mov Ax,1
  838.           Endif
  839.  
  840.          ;the IFN condition is true, ADD DX,CX
  841.          ;is not assembled
  842.           Ifn -6     ;value not equal to zero, true
  843.            Add Dx,Cx
  844.           Endif
  845.  
  846.        The NEXTIF directive works like an ENDIF/IF combination.  If a
  847.        NEXTIF is encountered, the present present conditional block of
  848.        code is finished (like an ENDIF) and a new conditional block is
  849.        started (like an IF).  NEXTIF, like IF, has a single conditional
  850.        operand.  Any number of NEXTIF's may follow an IF. NEXTIF's are
  851.        most useful for defining a sequential series of source code blocks
  852.        in situations where none, some, or all of the blocks may be
  853.        assembled or skipped.
  854.  
  855.  
  856.        20                                          Conditional Directives
  857.  
  858.          ;the NOP and SUB DI,SI are assembled
  859.           If 1
  860.            Nop
  861.           Nextif 0
  862.            Mov Ax,Dx
  863.           Nextif 1
  864.            Sub Di,Si
  865.           Endif
  866.  
  867.        The ELSEIF directive can be thought of as "if the previous IF was
  868.        false and if the condition is true, then assemble the following
  869.        code."  In other words, the conditional operand will only be
  870.        tested if the previous IF was false.  ELSEIF has a single
  871.        conditional operand.  Any number of ELSEIF's may follow an IF.
  872.        ELSEIF's are most useful for defining a sequential series of
  873.        source code blocks in situations where only one of the blocks will
  874.        be assembled and the remaining blocks skipped.
  875.  
  876.          ;the DEC AL is assembled
  877.           If 0
  878.            Nop
  879.           Elseif 1  ;previous IF=false and operand=true, true
  880.            Dec Al
  881.           Endif
  882.  
  883.          ;only the INC BP is assembled, the ELSEIF directives
  884.          ;default to false because the first IF is true
  885.           If 1
  886.            Inc Bp
  887.           Elseif 1
  888.            Nop
  889.           Elseif 1
  890.            Call Near [Ax]
  891.           Endif
  892.  
  893.          ;only the NOP is assembled
  894.           If 0
  895.            Inc Bp
  896.           Elseif 1
  897.            Nop
  898.           Elseif 1
  899.            Call Near [Bx]
  900.           Endif
  901.  
  902.        The ELSE directive is just like an ELSEIF directive where the
  903.        condition is always true.  The source code after the ELSE is
  904.        automatically assembled if the previous IF was false, otherwise
  905.        the source code is skipped.  Only a single ELSE should follow an
  906.        IF.  ELSE's are used when a section of code should be assembled
  907.        either one way or another.
  908.  
  909.  
  910.        Conditional Directives                                          21
  911.  
  912.          ;the SUB WORD [DI],6 is assembled
  913.           If 0
  914.            Mov Word [Di],0
  915.           Else
  916.            Sub Word [Di],6
  917.           Endif
  918.  
  919.        The NEXTIF, ELSEIF, and ELSE directives generally should not be
  920.        mixed together in a single conditional structure.  The only
  921.        exception may be using ELSEIF's or a single ELSE after a NEXTIF,
  922.        or a single ELSE after an ELSEIF.  Remember that all conditional
  923.        structures start with an IF and end with an ENDIF.  The ENDIF must
  924.        come after any intermediary conditional directives (NEXTIF,
  925.        ELSEIF, and ELSE).
  926.  
  927.          ;the SUB DI,10 and SUB SI,30 are assembled
  928.           If 1
  929.            Sub Di,10
  930.           Nextif 0
  931.            Add Si,20
  932.           Else
  933.            Sub Si,30
  934.           Endif
  935.  
  936.          ;the MOV DL,AL is assembled
  937.           If 0
  938.            Mov Dl,Cl
  939.           Elseif 0
  940.            Mov Dl,Bl
  941.           Else
  942.            Mov Dl,Al
  943.           Endif
  944.  
  945.  
  946.        22                                     Nested Conditional Assembly
  947.  
  948.                            Nested Conditional Assembly
  949.  
  950.        Conditional statements may be nested up to ten deep.  An IF or IFN
  951.        following an IF, IFN, NEXTIF, ELSEIF, or ELSE, but before the
  952.        ENDIF, starts a nested conditional structure.  The NEXTIF, ELSEIF,
  953.        ELSE, and ENDIF directives always match the last IF or IFN.  The
  954.        nested conditional code continues until its ENDIF is reached.
  955.  
  956.          ;only the last SUB DX,DX is assembled, the
  957.          ;remaining code is skipped because of the
  958.          ;initial false IF; comments on conditional
  959.          ;statements that say "true" or "false" are
  960.          ;actually evaluated, comments that say "skipped"
  961.          ;aren't evaluated because of a previous
  962.          ;false conditional statement
  963.           If 0             ;false
  964.            Add Dx,Dx
  965.            Ifn 0           ;skipped
  966.             Add Ax,Ax
  967.            Else            ;skipped
  968.             Sub Ax,Ax
  969.            Endif           ;end of nested code
  970.           Else             ;true
  971.            Sub Dx,Dx       ;line is assembled
  972.           Endif
  973.  
  974.  
  975.        Nested Conditional Assembly                                     23
  976.  
  977.          ;... and a more complicated nesting example,
  978.          ;only the ADD AX,AX is assembled
  979.           If 0             ;false
  980.            Nop
  981.           Elseif 0         ;false
  982.            Nop
  983.           Else             ;true
  984.            If 0            ;false
  985.             Nop
  986.             Ifn 0          ;skipped
  987.              Nop
  988.             Nextif 0       ;skipped
  989.              Nop
  990.             Else           ;skipped
  991.              Nop
  992.             Endif
  993.            Elseif 1        ;true
  994.             Ifn 1          ;false
  995.              Nop
  996.             Nextif 0       ;false
  997.              Nop
  998.             Nextif 1       ;true
  999.              If 1          ;true
  1000.               Add Ax,Ax    ;line is assembled
  1001.              Else          ;false
  1002.               Nop
  1003.              Endif
  1004.             Endif
  1005.            Elseif 1        ;false
  1006.             Nop
  1007.            Endif
  1008.           Endif
  1009.  
  1010.  
  1011.        24                                           Conditional Operators
  1012.  
  1013.                               Conditional Operators
  1014.  
  1015.        Conditional operators return a true or false value after comparing
  1016.        two immediate data operands.  Conditional operators are used for
  1017.        evaluating and comparing conditional operands.
  1018.  
  1019.        Conditional operators check for ranges or particular values
  1020.        through the use of: "<", ">", and "=".  They work like normal
  1021.        operators, except that they return either FFFFH for true or 0 for
  1022.        false.
  1023.  
  1024.          ;the SHR CX is assembled, since one is equal
  1025.          ;to one; it may seem silly to write "1=1",
  1026.          ;but maybe it was originally "Parm=1", inside
  1027.          ;of a macro, where PARM is a macro parameter that
  1028.          ;may be different each time the macro is called
  1029.           If 1=1
  1030.            Shr Cx
  1031.           Endif
  1032.  
  1033.          ;the SHR CX is assembled, only the 2<3 is true
  1034.           If 2 = 3
  1035.            Shr Ax
  1036.           Nextif 2 > 3
  1037.            Shr Bx
  1038.           Nextif 2 < 3
  1039.            Shr Cx
  1040.           Endif
  1041.  
  1042.          ;the CLC is assembled; the condition is true
  1043.          ;because (2>2) = 0, (2=2) = 0FFFFH, so the
  1044.          ;condition is the same as 0 OR 0FFFFH, which is
  1045.          ;equal to 0FFFFH, which is true; this construction
  1046.          ;creates a "greater or equal to" condition;
  1047.          ;all the various numerical comparisons can be
  1048.          ;constructed using logical operators and parenthesis
  1049.           If (2 > 2) Or (2 = 2)
  1050.            Clc
  1051.           Endif
  1052.  
  1053.  
  1054.        Conditional Operand Testing                                     25
  1055.  
  1056.                            Conditional Operand Testing
  1057.  
  1058.        The functions TYPE, VALUE, and SIZE are used to check for specific
  1059.        operand qualities.  Each of these functions return a 16 bit value
  1060.        that corresponds to a particular attribute of its argument.
  1061.  
  1062.        The type represents how the operand is interpreted (register,
  1063.        immediate data, near label, etc.).  The value may be a number to
  1064.        distinguish a register from another registers, the location of a
  1065.        label, or the actual value of an immediate data number.  The size
  1066.        is how many bits the register or memory location represents, or
  1067.        the number of bits that an immediate data number can represented
  1068.        by.  The type and size work on a bit by bit basis, that is, a
  1069.        particular bit represents a particular type or size.  An operand
  1070.        may be represented by more than one type or size (i.e. have
  1071.        multiple bits set).  Two operands are identical only if their
  1072.        type, value, and size are all identical.
  1073.  
  1074.        Operands can be tested for certain characteristics by comparing
  1075.        the bit settings to those of known operands.  It can be a bit
  1076.        tricky to test for the exact conditions you want, some
  1077.        experimentation may be necessary.  For the most part, if the any
  1078.        of the type or size bits match, the operands will be compatible in
  1079.        size or type.
  1080.  
  1081.        For the following examples, assume that P1 and P2 are macro
  1082.        parameters passed to the conditional statement:
  1083.  
  1084.          ;the following is true only if P1 and P2 are
  1085.          ;identical, the equates are used to make it
  1086.          ;fit all on one line
  1087.  
  1088.          P_Type Equ Type(P1) = Type(P2)
  1089.          P_Size Equ Size(P1) = Size(P2)
  1090.          P_Value Equ Value(P1) = Value(P2)
  1091.           If P_Type And P_Size And P_Value
  1092.  
  1093.          ;the following is true only if P1 is a non-
  1094.          ;segment register (a segment register is not
  1095.          ;not necessarily compatible with a normal
  1096.          ;register); only matching bits will make the
  1097.          ;result non-zero (true), and only
  1098.          ;non-segment registers have matching bits
  1099.           If Type(P1) And Type(Ax)
  1100.  
  1101.          ;the following is true only if P1 IS a
  1102.          ;segment register, the opposite of above
  1103.           If Type(P1) And Type(Ds)
  1104.  
  1105.  
  1106.        26                                     Conditional Operand Testing
  1107.  
  1108.          ;the following is true only if P1 is AX or
  1109.          ;AL; this statement is testing for equality,
  1110.          ;not just matching bits; a normal register
  1111.          ;wouldn't work because AX has an extra bit
  1112.          ;set (which defines it as the accumulator)
  1113.           If Type(P1) = Type(Ax)
  1114.  
  1115.          ;the following is true only if P1 is AL; like
  1116.          ;above, the accumulator type is tested for, but
  1117.          ;also the size must be the same as CH
  1118.           If (Type(P1) = Type(Ax)) And (Size(P1) = Size(Ch))
  1119.  
  1120.          ;you might think that the following is true if P1
  1121.          ;is any non-segment eight bit register, since it
  1122.          ;checks for compatible types and compatible sizes;
  1123.          ;unfortunately it doesn't necessarily work; the
  1124.          ;type and size comparisons each produce a bit
  1125.          ;pattern; those patterns individually, if
  1126.          ;compatible, are an arbitrary non-zero; there is
  1127.          ;no guarantee that these the two individually
  1128.          ;compatible bit patterns are compatible with
  1129.          ;each other
  1130.           If (Type(P1) And Type(Dx)) And (Size(P1) And Size(Dh))
  1131.  
  1132.          ;instead you can write the previous statement in
  1133.          ;the following manner; this statement, like the
  1134.          ;above, tests the size and type for compatibility,
  1135.          ;but then compares the result to zero; the type
  1136.          ;and size comparisons now return FFFFH if they
  1137.          ;are false (equal to zero), and 0 if they are
  1138.          ;true; now the two results can then be compared;
  1139.          ;since we want a positive result to be true,
  1140.          ;rather than a negative one, the entire
  1141.          ;expression must be placed within a NOT
  1142.           If Not((Type(P1) And Type(Dx)=0) And (Size(P1) And Size(Dh)=0))
  1143.  
  1144.          ;the above statement can more easily be written
  1145.          ;with the IFN directive as follows
  1146.           Ifn (Type(P1) And Type(Dx)=0) And (Size(P1) And Size(Dh)=0)
  1147.  
  1148.        More examples of conditional operand testing are provided under
  1149.        Conditional Macros.
  1150.  
  1151.  
  1152.        Macros                                                          27
  1153.  
  1154.                                      Macros
  1155.  
  1156.        A macro is a type of programmer defined routine.  A macro consists
  1157.        of a symbol that has some number of source lines assigned to it.
  1158.        The programmer creates a macro by assigning a section of code to a
  1159.        symbol.  Any time the assembler encounters the symbol as an
  1160.        instruction, the source code assigned to it is inserted into the
  1161.        program.  A macro may be used any number of times and at any
  1162.        location in the program.  In addition, the macro may have some
  1163.        number of "operands," which are passed as parameters to the
  1164.        inserted source code.  Macros are often used in conjunction with
  1165.        conditional assembly to create routines that adjust to different
  1166.        parameters.
  1167.  
  1168.        Macros are useful for inserting sections of code that are used
  1169.        several times in a single program.  Macros are also used to define
  1170.        a standard set of routines that are used by many different
  1171.        programs.  By including a file with commonly used macro
  1172.        declarations, the programmer can use only those macros that are
  1173.        needed by that particular program.  Macros only create object code
  1174.        by the source lines they insert, that is, the macro declarations
  1175.        themselves do not take up any space in the assembled program.
  1176.  
  1177.  
  1178.        28                                                 Defining Macros
  1179.  
  1180.                                  Defining Macros
  1181.  
  1182.        Macros may be defined anywhere within the program, except inside
  1183.        of other macro declarations.  The MACRO directive starts a macro
  1184.        declaration.  The required symbol declaration becomes the name of
  1185.        the macro.  Any number of operands may follow the MACRO directive.
  1186.        These operands are used to pass parameters into the macro.
  1187.        Whenever the macro is invoked, the parameter names are replaced
  1188.        (inside of the macro) by whatever corresponding operands where
  1189.        placed after the macro name.  The parameter names are local to the
  1190.        macro and need only be unique within that macro, otherwise all the
  1191.        normal restrictions to symbol declarations apply.  The parameters
  1192.        names should be single fields separated by commas (no expressions
  1193.        or functional operands).
  1194.  
  1195.        Any number of source lines may follow the MACRO directive.  Macro
  1196.        declarations are stored internally, and are thus limited by
  1197.        memory.  If the macro area becomes full, the assembly will
  1198.        terminate and display the appropriate error message.  The entire
  1199.        source line, including all spaces, non-standard control
  1200.        characters, and extended ASCII characters, are preserved
  1201.        throughout the macro storage and expansion.
  1202.  
  1203.        Symbols may be defined normally within macros.  Symbols defined
  1204.        within a macro are local and cannot be accessed outside of that
  1205.        macro.  The symbols need only be unique within that macro.  Local
  1206.        equates may be defined using the macro parameters.
  1207.  
  1208.        All 8086 instructions and assembly directives may be used within
  1209.        macros.  Macros may also be invoked within other macros.  You can
  1210.        even have a macro call itself recursively.  Conditional statements
  1211.        within macros apply to the overall conditional structure of the
  1212.        program, in other words, an ENDIF inside of a macro could be
  1213.        matched to an IF that appeared sometime outside and before the
  1214.        macro.  Note that macros are not expanded if they are in false
  1215.        conditional code, except for conditional macros, see Conditional
  1216.        Macros.
  1217.  
  1218.        A operand field inside of a macro may either be a parameter name,
  1219.        one of the predefined operand types, a local symbol, or a global
  1220.        symbol.  Parameter names take precedence over all other fields and
  1221.        are replaced before any interpretation occurs.  Local symbols take
  1222.        precedence over global symbols.  When specifying parameter names,
  1223.        if it is possible that the parameter will receive a nul string, it
  1224.        is a good idea to put parenthesis around the name.  This allows
  1225.        the line to be parsed correctly if a nul parameter is passed.
  1226.  
  1227.        Conditional statements can be used to test for valid parameters.
  1228.        If a parameter is not valid, it can be flagged with the ERROR
  1229.        directive.
  1230.  
  1231.        A macro declaration is ended by the ENDM directive.
  1232.  
  1233.  
  1234.        Defining Macros                                                 29
  1235.  
  1236.          ;defines a macro to move a value into segment
  1237.          ;register, especially immediate date, since
  1238.          ;immediate data cannot be moved directly into
  1239.          ;a segment register
  1240.  
  1241.          Mov_Seg Macro Segment_Reg, Location
  1242.           Push Ax
  1243.           Mov Ax, Location
  1244.           Mov Segment_Reg, Ax
  1245.           Pop Ax
  1246.           Endm
  1247.  
  1248.          ;defines a macro to execute an interrupt, also
  1249.          ;if a function number is provided, it is placed
  1250.          ;in AH; if the interrupt number is not immediate
  1251.          ;data, it is flagged.
  1252.  
  1253.          Interrupt Macro Int_Num, Func_Num
  1254.           If Type(Int_Num) And Type(0)
  1255.            Ifn Type(Func_Num) = Type()
  1256.             Mov Ah, Func_Num
  1257.            Endif
  1258.            Int Int_Num
  1259.           Else
  1260.            Error 'Interrupt must be immediate data'
  1261.           Endif
  1262.           Endm
  1263.  
  1264.  
  1265.        30                                                 Invoking Macros
  1266.  
  1267.                                  Invoking Macros
  1268.  
  1269.        Macros are invoked by using the macro name as an instruction.  Any
  1270.        operands will be passed as parameters.  The operands may be any
  1271.        kind, of any length, including expressions and functional
  1272.        operands.  Parameters are assigned in the order in which they were
  1273.        defined in the macro declaration.  Extra operands are ignored,
  1274.        missing parameters pass a nul string.  A parameter may be skipped
  1275.        and be assigned a nul string by placing a comma without an
  1276.        operand.
  1277.  
  1278.        Parameter names are blindly replaced in the macro source lines by
  1279.        their passed parameters.  Nul parameters simply remove the
  1280.        parameter name.  The resulting source line may be longer or
  1281.        shorter than the original.  Unnecessary spaces are removed from
  1282.        the parameters, so they may not look exactly the same in the
  1283.        source line as they did when they were first specified as
  1284.        operands.
  1285.  
  1286.        Macros are not normally expanded if the present source code is
  1287.        being skipped because of a false conditional statement.  Any
  1288.        conditional statements within that macro will be ignored.
  1289.        Conditional macros, on the other hand, are expanded under those
  1290.        circumstances, see Conditional Macros.
  1291.  
  1292.          ;defines a macro to declare three bytes, any
  1293.          ;missing parameters are declared as zero
  1294.  
  1295.          Dec_Bytes Macro Byte1, Byte2, Byte3
  1296.           Ifn Type(Byte1) = Type()
  1297.            Db Byte1
  1298.           Else
  1299.            Db 0
  1300.           Endif
  1301.           Ifn Type(Byte2) = Type()
  1302.            Db Byte2
  1303.           Else
  1304.            Db 0
  1305.           Endif
  1306.           Ifn Type(Byte3) = Type()
  1307.            Db Byte3
  1308.           Else
  1309.            Db 0
  1310.           Endif
  1311.           Endm
  1312.  
  1313.           Dec_Bytes         ;produces 000000
  1314.  
  1315.           Dec_Bytes 1       ;produces 010000
  1316.           Dec_Bytes ,2      ;produces 000200
  1317.           Dec_Bytes ,,3     ;produces 000003
  1318.  
  1319.  
  1320.        Invoking Macros                                                 31
  1321.  
  1322.           Dec_Bytes 1,2     ;produces 010200
  1323.           Dec_Bytes ,2,3    ;produces 000203
  1324.           Dec_Bytes 1,,3    ;produces 100003
  1325.  
  1326.           Dec_Bytes 1,2,3   ;produces 010203
  1327.  
  1328.  
  1329.        32                                                   Nested Macros
  1330.  
  1331.                                   Nested Macros
  1332.  
  1333.        Macros may be nested up to ten deep.  A macro invocation inside of
  1334.        another macro works no differently than any other macro
  1335.        invocation.  When the nested macros finishes, the original macro
  1336.        resumes.  A macro may even call itself recursively, though, unless
  1337.        the recursion is controlled by conditional statements, an error
  1338.        will occur when the maximum nest level is exceeded.
  1339.  
  1340.        Parameters may be passed to successive macro levels.  Local
  1341.        symbols within a macro cannot be accessed by any nested macros
  1342.        within it.
  1343.  
  1344.          ;defines a macro that uses recursion to produce
  1345.          ;a specified number of single shift right
  1346.          ;instructions, the macro calls itself as long as
  1347.          ;the count parameter is greater than zero; note
  1348.          ;that the count cannot exceed nine (assuming it is
  1349.          ;not called from within another macro), otherwise
  1350.          ;the macros will nest too deeply
  1351.  
  1352.          Shift_Right Macro Operand, Count
  1353.           If Count > 0
  1354.            Shr Operand
  1355.            Shift_Right Operand, Count-1
  1356.           Endif
  1357.           Endm
  1358.  
  1359.  
  1360.        Conditional Macros                                              33
  1361.  
  1362.                                Conditional Macros
  1363.  
  1364.        Conditional macros are similar to normal macros.  They are
  1365.        declared with MACROC instead of MACRO.  The purpose of conditional
  1366.        macros are to create custom conditional statements.  Conditional
  1367.        macros do three things that normal macros don't: the line invoking
  1368.        the macro is not listed (like like a conditional statement), the
  1369.        macro expansion is not listed (by an implicit EXPAND-), and the
  1370.        macros are expanded in false conditional code.  Generally one
  1371.        would declare the macro with just a single conditional line that
  1372.        expresses the relationship that is desired.
  1373.  
  1374.          ;defines an "if the parameter doesn't exist" statement by
  1375.          ;testing to see if the type returned for the parameter
  1376.          ;is the same as the type returned for a nul operand
  1377.  
  1378.          If_None Macroc Parameter
  1379.           If Type(Parameter) = Type()
  1380.           Endm
  1381.  
  1382.          ;defines an "if the parameter exists" statement
  1383.          ;by taking the opposite result of the declaration above
  1384.  
  1385.          If_Exist Macroc Parameter
  1386.           Ifn Type(Parameter) = Type()
  1387.           Endm
  1388.  
  1389.          ;defines an "if the parameter is a byte" statement
  1390.          ;by testing if any of the same size bits are set in the
  1391.          ;size of the parameter and the size of a byte value
  1392.  
  1393.          If_Byte Macroc Parameter
  1394.           If Size(Parameter) And Size(Byte 0)
  1395.           Endm
  1396.  
  1397.          ;defines an "if the sizes of the parameters are
  1398.          ;compatible" statement by testing for matching
  1399.          ;size bits
  1400.  
  1401.          If_Compatible_Size Macroc Parameter1, Parameter2
  1402.           If Size(Parameter1) And Size(Parameter2)
  1403.           Endm
  1404.  
  1405.          ;defines an "if the parameters are identical"
  1406.          ;statement testing if the type, value, and size
  1407.          ;are identical; equates are used to simplify and
  1408.          ;shorten the final statement
  1409.  
  1410.          If_Same Macroc Op1, Op2
  1411.          Stype Equ Type(Op1) = Type(Op2)
  1412.          Ssize Equ Size(Op1) = Size(Op2)
  1413.          Svalue Equ Value(Op1) = Value(Op2)
  1414.           If Stype And Ssize And Svalue
  1415.           Endm
  1416.  
  1417.  
  1418.        34                                               Listing of Macros
  1419.  
  1420.                                 Listing of Macros
  1421.  
  1422.        Macro expansions are listed like any other source line.  The
  1423.        special list indicator byte is a plus (+) in inserted macros
  1424.        lines.  The present macro nest level is displayed when the macro
  1425.        is first invoked.  This number is shown in the area normally
  1426.        reserved for the object code.  There is no way to tell when a
  1427.        nested macro ends within another macro.
  1428.  
  1429.        The listing of inserted macro lines may be globally suppressed or
  1430.        enabled with the EXPAND- and EXPAND+ directives.  The listing of
  1431.        individual macros may also be controlled by these directives.  If
  1432.        EXPAND- and EXPAND+ directives appear in a macro, they only affect
  1433.        that macro (and any nested macros).  EXPAND- and EXPAND+ do not
  1434.        have any effect if the source code is not otherwise being listed.
  1435.        Note that EXPAND- and EXPAND+ only affect the listing of macros,
  1436.        not the actual expansion of macros.
  1437.  
  1438.        Errors occurring within macro expansions are treated normally,
  1439.        except that the error message shows the last real line number and,
  1440.        if in an included file, the name of the source file.  The line
  1441.        number is in parenthesis following the error message.
  1442.  
  1443.          ;defines a macro that adds the parameters
  1444.          ;together and puts the result in DX; this
  1445.          ;macro is never listed because of the
  1446.          ;EXPAND-
  1447.  
  1448.          Adder Macro Parameter1, Parameter2
  1449.           Expand-
  1450.           Mov Dx,Parameter1
  1451.           Add Dx,Parameter2
  1452.           Endm
  1453.  
  1454.        Data                                                            35
  1455.  
  1456.                                       Data
  1457.  
  1458.        Data that is used by the program during execution must be placed
  1459.        in the program by declaration.  Data that is declared includes
  1460.        things like numbers and strings.  This is in contrast to the
  1461.        declaration of macros and equates which are only used when the
  1462.        program is assembled.  The DB, DW, and DS directives are used to
  1463.        make data declarations.
  1464.  
  1465.        DB is used to declare byte values, strings, words, and
  1466.        combinations of all three.  If a symbol is declared with the DB
  1467.        directive, it becomes an eight bit memory reference label.  The
  1468.        data declared by the DB may be accessed through the label.  Values
  1469.        are declared as bytes if possible, otherwise they are declared as
  1470.        words.  The BYTE and WORD functions may be used to explicitly
  1471.        define the number of bits used in declaring the data.
  1472.  
  1473.        DW is used to declare word values.  If a symbol is declared with
  1474.        the DW directive, it becomes a sixteen bit memory reference label.
  1475.        The data declared by the DW may be accessed through the label.
  1476.        Values are always declared as words, even if they may be bytes.
  1477.  
  1478.        Though WASM can only intialize 8 or 16 bit values, you can always
  1479.        use DB and DW with a LABEL to declare other sized data.  For
  1480.        instance, this declares a double word of data:
  1481.  
  1482.          ;declare the double word 12345678h
  1483.          Data Label Dword              ;create the label
  1484.           Dw 5678h             ;low word of data
  1485.           Dw 1234h             ;high word of data
  1486.  
  1487.        DS is used to declare any number of identical bytes.  If a symbol
  1488.        is declared with the DS directive, the it becomes a memory
  1489.        reference label with no size.  The size should be specified
  1490.        whenever this label is accessed (via the size functions BYTE,
  1491.        WORD, DWORD, etc.).  The LABEL directive may be used to declare a
  1492.        label of a particular type and size immediately before the DS.
  1493.  
  1494.        Word values are always stored low byte first, with the exception
  1495.        of two byte strings.  Assuming '1' = 31H and 'B' = 42H, the hex
  1496.        number 3142H will be stored as 4231H, though '1B' will be stored
  1497.        as 3142H.  The reverse format is how word numbers should be
  1498.        stored.  If for some reason a word value is stored as two separate
  1499.        bytes (using DB), the low byte should always be stored first,
  1500.        otherwise the number will be backwards for arithmetic operations.
  1501.  
  1502.        Declarations may be made anywhere in the program.  Since
  1503.        declarations produce non-executable object code, they should not
  1504.        be placed in a location where they might be interpreted as part of
  1505.        the code.  Branch the program around declarations, or put them at
  1506.        the end of the program or routine, after the executable code.
  1507.  
  1508.  
  1509.        36                                                            Data
  1510.  
  1511.        Examples of data declarations:
  1512.  
  1513.          ;declare a byte
  1514.           Db -5
  1515.  
  1516.          ;declare a byte and then a word value
  1517.           Db Byte 0, Word 0
  1518.          ;... or just
  1519.           Db 0, Word 0
  1520.  
  1521.          ;declare a string
  1522.           Db 'This is the string'
  1523.  
  1524.          ;declare some words
  1525.           Dw 0, 1, 2, 3, 65533, 65534, 65535
  1526.  
  1527.          ;the following declaration can be accessed through VALUES
  1528.          Values Db 100,-20, 36/10, 0, 010100110b
  1529.  
  1530.          ;this instruction accesses the numbers
  1531.          ;in VALUES above based on an index in BX
  1532.           Mov Al, [Values + Bx]  ;load number
  1533.  
  1534.          ;declare storage
  1535.           Ds 10          ;ten bytes of 00
  1536.           Ds 100, 0ffh   ;a hundred bytes of FFH
  1537.  
  1538.  
  1539.        Assembly Directives                                             37
  1540.  
  1541.                                Assembly Directives
  1542.  
  1543.        Assembly directives are instructions to control the assembly, they
  1544.        do not encode into 8086 machine language instructions, though some
  1545.        of the directives do produce object code.  Assembly directives are
  1546.        implemented the same way as normal instructions.
  1547.  
  1548.        This section describes all the assembly directives.  Most of the
  1549.        directives are also described in sections pertinent to their
  1550.        operation.
  1551.  
  1552.        The major categories of assembly directives are those that are
  1553.        used to declare symbols (EQU, LABEL, ORG), those that declare data
  1554.        (DB, DS, DW), those that declare procedures and macros (PROC,
  1555.        ENDP, MACRO, MACROC, ENDM), those used to control conditional
  1556.        assembly (ELSE, ELSEIF, ENDIF, IF, IFN, NEXTIF), those that
  1557.        control the assembly listing (EXPAND+, EXPAND-, LINSIZE, LIST+,
  1558.        LIST-, PAGE, PAGE+, PAGE-, PAGESIZE, SUBTITLE, SYMDUMP+, SYMDUMP-,
  1559.        TITLE), those that control error flagging and detection (ERROR,
  1560.        ERRORMAX, FLAGALL+, FLAGALL-, JUMP+, JUMP-, UNUSED+, UNUSED-), and
  1561.        some miscellaneous ones (INCLUDE, RESETC).
  1562.  
  1563.        ******************************************************************
  1564.  
  1565.        DB value/string, ...
  1566.  
  1567.        Declare byte.
  1568.  
  1569.        Places literal bytes of data into the assembled code.
  1570.  
  1571.        DB may have any number of operands, as long as they fit on the
  1572.        line.  The value of each operand is placed sequentially into the
  1573.        assembled code.  The operands can be immediate data or strings.
  1574.        Immediate data operands are declared as bytes if possible,
  1575.        otherwise they are declared as words.  Strings are inserted just
  1576.        as they appear (minus the string delimiters).
  1577.  
  1578.        See Data.
  1579.  
  1580.          ;the following declares a sentence with its
  1581.          ;length preceding it, including a carriage
  1582.          ;return and linefeed at the end of the sentence;
  1583.          ;the BYTE function is needed to make the length
  1584.          ;an explicit eight bit value
  1585.  
  1586.          A
  1587.           Db Byte(Offset B - Offset A - 1),'The sentence.',10,13
  1588.          B
  1589.  
  1590.          ;this declares a byte FFH and then a word FFFFH
  1591.           Db  -1, Word -1
  1592.  
  1593.  
  1594.        38                                             Assembly Directives
  1595.  
  1596.        ******************************************************************
  1597.  
  1598.        DS bytes [, value]
  1599.  
  1600.        Declare storage.
  1601.  
  1602.        Places some number of identically initialized bytes into the
  1603.        assembled code.
  1604.  
  1605.        DS can have one or two operands.  The first operand is the number
  1606.        of bytes to declare and the second is the value that the storage
  1607.        should be initialized to.  The initialization value is optional,
  1608.        and, if absent, the storage is initialized to zero.  The number of
  1609.        bytes to declare must be immediate data (0 to 65535).  The
  1610.        initialization value must be eight bit immediate data.
  1611.  
  1612.        See Data.
  1613.  
  1614.          ;declare a thousand bytes of FFH
  1615.           Ds 1000, 0ffh
  1616.  
  1617.        ******************************************************************
  1618.  
  1619.        DW value, ...
  1620.  
  1621.        Declare word.
  1622.  
  1623.        Places literal words of data into the assembled code.
  1624.  
  1625.        DW can have any number of operands, as long as they fit on the
  1626.        line.  The value of each operand is placed sequentially into the
  1627.        assembled code.  The operands must be immediate data.  The
  1628.        operands are always declared as words, even if they could be
  1629.        bytes.
  1630.  
  1631.        See Data.
  1632.  
  1633.          ;this sort of construction can be useful
  1634.          ;for creation a table of addresses, note
  1635.          ;that this particular example would work
  1636.          ;equally well with DB
  1637.           Dw Offset Subrt1, Offset Subrt2
  1638.  
  1639.        ******************************************************************
  1640.  
  1641.        ELSE
  1642.  
  1643.        Conditional "else."
  1644.  
  1645.        Assembles the following source code only if the previous IF
  1646.        directive was false.
  1647.  
  1648.        Requires no operands.
  1649.  
  1650.  
  1651.        Assembly Directives                                             39
  1652.  
  1653.        See Conditional Assembly.
  1654.  
  1655.          ;the code after the ELSE is carried out
  1656.          ;if NUMBER is not greater than 10
  1657.           If Number > 10
  1658.            Mov Ax, Bx
  1659.           Else
  1660.            Mov Bx, Ax
  1661.           Endif
  1662.  
  1663.        ******************************************************************
  1664.  
  1665.        ELSEIF condition
  1666.  
  1667.        Conditional "else if."
  1668.  
  1669.        Assembles the following source code only if the previous IF
  1670.        directive was false and the condition is true.
  1671.  
  1672.        ELSEIF requires a single immediate data operand.  This operand is
  1673.        the condition to test.
  1674.  
  1675.        See Conditional Assembly.
  1676.  
  1677.          ;only one of the following are true:
  1678.          ;if OPTION is equal to zero, CALL SUBRT1 is
  1679.          ;assembled; if OPTION is equal to one,
  1680.          ;CALL SUBRT2 is assembled; if OPTION is equal
  1681.          ;to two, CALL SUBRT3 is assembled
  1682.           If Option=0
  1683.            Call Subrt1
  1684.           Elseif Option=1
  1685.            Call Subrt2
  1686.           Elseif Option=2
  1687.            Call Subrt3
  1688.           Endif
  1689.  
  1690.        ******************************************************************
  1691.  
  1692.        ENDIF
  1693.  
  1694.        End of conditional structure.
  1695.  
  1696.        Finishes a conditional structure started by an IF directive.
  1697.  
  1698.        Requires no operands.
  1699.  
  1700.  
  1701.        40                                             Assembly Directives
  1702.  
  1703.        See Conditional Assembly.
  1704.  
  1705.          ;ENDIF finishes the conditional structure,
  1706.          ;so the CLC is assembled no matter what
  1707.           If Type(Parameter)=Type(Ax)
  1708.            Sub Ax, Ax
  1709.           Endif
  1710.           Clc
  1711.  
  1712.        ******************************************************************
  1713.  
  1714.        ENDM
  1715.  
  1716.        End of macro.
  1717.  
  1718.        Finishes a macro declaration started by a MACRO or MACROC
  1719.        directive.
  1720.  
  1721.        Requires no operands.
  1722.  
  1723.        See Macros.
  1724.  
  1725.          ;the ENDM finishes the rather simple declaration
  1726.          ;of the macro NUL_INST
  1727.  
  1728.          Nul_Inst Macro
  1729.           Nop
  1730.           Endm
  1731.  
  1732.        ******************************************************************
  1733.  
  1734.        ENDP
  1735.  
  1736.        End of procedure.
  1737.  
  1738.        Finishes a procedure declaration started by a PROC directive.
  1739.  
  1740.        Requires no operands.
  1741.  
  1742.        See Procedures.
  1743.  
  1744.          ;the ENDP finishes the declaration of the
  1745.          ;procedure SUBRT
  1746.  
  1747.          Subrt Proc Near
  1748.           Xchg Ax, [Si]
  1749.           Ret
  1750.           Endp
  1751.  
  1752.        ******************************************************************
  1753.  
  1754.        EQU value
  1755.  
  1756.        Equate a value.
  1757.  
  1758.  
  1759.        Assembly Directives                                             41
  1760.  
  1761.        Defines a symbol that may be used anywhere in place of a specified
  1762.        value.
  1763.  
  1764.        EQU requires a single immediate data operand and the symbol to be
  1765.        equated.  The operand becomes equated to the symbol.
  1766.  
  1767.        EQU is useful for making the source code more readable by
  1768.        replacing arbitrary numbers with meaningful symbols.  The value of
  1769.        the equate generally should not reference any symbols that have
  1770.        not been defined yet in the source code.  This means that the
  1771.        value should not contain a forward reference to another equate, or
  1772.        use OFFSET when its argument has not yet been defined.
  1773.  
  1774.        See Symbols.
  1775.  
  1776.          ;equate the number 50 times 20, or 1000, to the
  1777.          ;symbol NUMBER, and then move NUMBER into AX
  1778.  
  1779.          Number Equ 50*20
  1780.           Mov Ax, Number
  1781.  
  1782.        ******************************************************************
  1783.  
  1784.        ERROR message
  1785.  
  1786.        Programmer defined error.
  1787.  
  1788.        Causes an error to occur using the specified message.
  1789.  
  1790.        ERROR requires a single string operand.  This operand becomes the
  1791.        error message.
  1792.  
  1793.        No line is displayed with the error message, the listing of the
  1794.        statement itself is suppressed.  The error is included in total
  1795.        number of errors at the end of the program.  ERROR is useful for
  1796.        flagging invalid macro parameters.
  1797.  
  1798.          ;defines a macro that checks for a missing operand;
  1799.          ;if the macro is invoked with the operand is missing,
  1800.          ;an error is displayed using an ERROR directive
  1801.  
  1802.          Mover Macro Op1
  1803.           If Type(Op1) = Type()
  1804.            Error 'Missing operand'
  1805.           Endif
  1806.           Endm
  1807.  
  1808.          ;this will cause the error
  1809.           Mover       ;invoked with no operands
  1810.  
  1811.  
  1812.        42                                             Assembly Directives
  1813.  
  1814.        ******************************************************************
  1815.  
  1816.        ERRORMAX number
  1817.  
  1818.        Maximum errors.
  1819.  
  1820.        Places an upper limit on the number of errors and comments
  1821.        occurring before the assembly is halted.
  1822.  
  1823.        ERRORMAX requires a single immediate data operand.  This operand
  1824.        becomes the new number of maximum allowed errors.
  1825.  
  1826.        The default is 65535.  Note that both errors and comments are
  1827.        counted.
  1828.  
  1829.          ;set the number of allowed errors to ten, if a tenth error
  1830.          ;or comment ever occurs, the assembly will be terminated
  1831.           Errormax 10
  1832.  
  1833.        ******************************************************************
  1834.  
  1835.        EXPAND+
  1836.        EXPAND-
  1837.  
  1838.        List macro expansions.
  1839.  
  1840.        When activated (EXPAND+), lines resulting from a macro expansion
  1841.        will be listed.  When deactivated (EXPAND-), lines resulting from
  1842.        a macro expansion will not be listed, only the line containing the
  1843.        macro invocation will be visible.
  1844.  
  1845.        Requires no operands.
  1846.  
  1847.        The default is EXPAND+.  EXPAND+ and EXPAND- directives that are
  1848.        within macros only apply to those macros.  Macros will not be
  1849.        listed regardless of the EXPAND+ and EXPAND- directives if the
  1850.        source code is not otherwise being listed.
  1851.  
  1852.        See Macros and Assembly Listing.
  1853.  
  1854.          ;macro expansions are globally listed because
  1855.          ;of the EXPAND+, except the defined macro TERMINATE
  1856.          ;explicitly suppresses only its own listing
  1857.           Expand+
  1858.  
  1859.          Terminate Macro
  1860.           Expand-
  1861.           Mov Ah, 4ch
  1862.           Int 21h
  1863.           Endm
  1864.  
  1865.  
  1866.        Assembly Directives                                             43
  1867.  
  1868.        ******************************************************************
  1869.  
  1870.        FLAGALL+
  1871.        FLAGALL-
  1872.  
  1873.        Undefined symbol flagging.
  1874.  
  1875.        When activated (FLAGALL+), an undefined symbol is flagged each
  1876.        time it is used, even if it has been flagged before.  When
  1877.        deactivated (FLAGALL-), an undefined symbol is only flagged the
  1878.        first time it is used.
  1879.  
  1880.        Requires no operands.
  1881.  
  1882.        The default is FLAGALL-.
  1883.  
  1884.          ;assuming BADSYM is undefined, it is flagged when
  1885.          ;it is moved to AX and BX, but not when it is
  1886.          ;moved to CX or DX, since it has been flagged
  1887.          ;previously and because of the FLAGALL-
  1888.           Flagall+
  1889.           Mov Ax, Badsym
  1890.           Mov Bx, Badsym
  1891.           Flagall-
  1892.           Mov Cx, Badsym
  1893.           Mov Dx, Badsym
  1894.  
  1895.        ******************************************************************
  1896.  
  1897.        IF condition
  1898.  
  1899.        Conditional "if."
  1900.  
  1901.        Assembles the following source code only if the condition is true.
  1902.  
  1903.        IF requires a single immediate data operand.  This operand is the
  1904.        condition to test.
  1905.  
  1906.        The IF directive starts a conditional structure. See Conditional
  1907.        Assembly.
  1908.  
  1909.          ;if COND is zero, the IN AX,DX will be assembled
  1910.           If Not(Cond)
  1911.            In Ax, Dx
  1912.           Endif
  1913.  
  1914.        ******************************************************************
  1915.  
  1916.        IFN condition
  1917.  
  1918.        Conditional "if not."
  1919.  
  1920.        Assembles the following source code only if the condition is
  1921.        false.
  1922.  
  1923.  
  1924.        44                                             Assembly Directives
  1925.  
  1926.        IFN requires a single immediate data operand.  This operand is the
  1927.        condition to test.
  1928.  
  1929.        The IFN directive starts a conditional structure.  IFN is the
  1930.        opposite of IF.  See Conditional Assembly.
  1931.  
  1932.          ;if COND is zero, the OUT DX,AX will be assembled
  1933.           If Cond
  1934.            Out Dx, Ax
  1935.           Endif
  1936.  
  1937.        ******************************************************************
  1938.  
  1939.        INCLUDE file
  1940.  
  1941.        Include source file.
  1942.  
  1943.        The specified file is inserted into the main source code
  1944.        immediately after the INCLUDE directive.
  1945.  
  1946.        INCLUDE requires a single string operand.  This operand should
  1947.        contain the name of the file to insert.  If no path is specified,
  1948.        the main source file path is used.  If no extension is specified,
  1949.        the extension of ASM is used.
  1950.  
  1951.        The included source code is not treated any differently than the
  1952.        rest of the program.  Included files may NOT be nested, which
  1953.        means that the file being inserted may not contain any INCLUDE
  1954.        directives.  Neither may INCLUDE's be used within macros.  INCLUDE
  1955.        is useful for inserting source code used by many different
  1956.        programs, like standard macro declarations.  INCLUDE can also be
  1957.        used to break up a source file into several smaller chunks, if,
  1958.        for instance, your text editor cannot handle the entire source
  1959.        file at once.
  1960.  
  1961.          ;the following directive inserts the file
  1962.          ;INCLUDE.INC, the source drive and path are
  1963.          ;used
  1964.           Include 'Source.Inc'
  1965.  
  1966.        ******************************************************************
  1967.  
  1968.        JUMP+
  1969.        JUMP-
  1970.  
  1971.        Short jump checking.
  1972.  
  1973.        When activated (JUMP+), all long near jump instructions will be
  1974.        flagged if a short near jump could be substituted.  When
  1975.        deactivated (JUMP-), long jumps that could be short jumps are not
  1976.        flagged.
  1977.  
  1978.        Requires no operands.
  1979.  
  1980.  
  1981.        Assembly Directives                                             45
  1982.  
  1983.        The default is JUMP-.  Substituting a short jump for a long jump
  1984.        does not logically change the program, but does make the assembled
  1985.        code one byte shorter.
  1986.  
  1987.          ;both of the following jumps could be
  1988.          ;JMPS (a short unconditional jump); the
  1989.          ;first JMP LABEL is not flagged, the
  1990.          ;second one is
  1991.           Jump-
  1992.           Jmp Label
  1993.           Jump+
  1994.           Jmp Label
  1995.          Label
  1996.  
  1997.        ******************************************************************
  1998.  
  1999.        LABEL type
  2000.  
  2001.        Label declaration.
  2002.  
  2003.        Defines a branch or memory reference label using the present
  2004.        location counter.
  2005.  
  2006.        LABEL requires a single operand and a symbol to be defined.  The
  2007.        operand NEAR or FAR is used for branch locations.  The operand
  2008.        BYTE, WORD, or DWORD is used for memory references of eight,
  2009.        sixteen, or thirty-two bit sizes, respectively.
  2010.  
  2011.        Explicitly defining a symbol as NEAR has the same effect as
  2012.        placing a symbol on an otherwise empty line or a line with some
  2013.        sort of operation (not a data declaration).  Explicitly declaring
  2014.        a symbol as BYTE or WORD has the same effect as placing a symbol
  2015.        on a byte (DB) or  word (DW) data declaration.  LABEL can be used
  2016.        in conjunction with the ORG directive to define labels independent
  2017.        of the actual code being assembled.
  2018.  
  2019.        See Symbols.
  2020.  
  2021.          ;this label ...
  2022.          Bran1 Label Near
  2023.          ;...is the same type as
  2024.          Bran2 Mov Ds, Dx
  2025.  
  2026.          ;and this ...
  2027.          Dat1 Label Word
  2028.          ;... produces the same sort of label as ...
  2029.          Dat2 Dw ?
  2030.  
  2031.  
  2032.        46                                             Assembly Directives
  2033.  
  2034.          ;the following causes MEM_SIZE to point at the word
  2035.          ;in program segment prefix that tells how many bytes
  2036.          ;are available in the segment; if you use this method
  2037.          ;to define any labels, make sure to reset the location
  2038.          ;counter back to its proper value before defining any
  2039.          ;other normal labels in the program
  2040.           Org 6
  2041.          Mem_Size Label Word
  2042.  
  2043.        ******************************************************************
  2044.  
  2045.        LINESIZE [length] [, code, ...]
  2046.  
  2047.        List line length.
  2048.  
  2049.        Sets the maximum number of characters in each list line.
  2050.  
  2051.        The optional first operand is the list line length.  The remaining
  2052.        optional eight bit immediate data operands are printer codes.
  2053.        These printer codes are sent directly to the printer if the list
  2054.        file is PRN.
  2055.  
  2056.        The default is 79.  The length must be in the range 45 to 158.
  2057.        The number of characters per line should only be set once in a
  2058.        program, though multiple LINESIZE directives may be used to send
  2059.        several bunches of printer codes.  If a list line would come out
  2060.        any longer than specified by the LINESIZE, it will be truncated.
  2061.        PAGESIZE can also be used to set the number of characters per
  2062.        line.
  2063.  
  2064.        See Assembly Listing.
  2065.  
  2066.          ;set up for IBM Graphics printer compressed font, the
  2067.          ;printer code (15) is sent if PRN is the list file
  2068.           Linesize 131, 15
  2069.  
  2070.        ******************************************************************
  2071.  
  2072.        LIST+
  2073.        LIST-
  2074.  
  2075.        Assembly listing.
  2076.  
  2077.        When activated (LIST+), a listing of the program will be
  2078.        generated.  When deactivated (LIST-), no listing will be
  2079.        generated.
  2080.  
  2081.        Requires no operands.
  2082.  
  2083.  
  2084.        Assembly Directives                                             47
  2085.  
  2086.        If a list file was specified at the start of the program, the
  2087.        default is LIST+.  If no list file was specified, no list will be
  2088.        generated (regardless of any LIST+ or LIST- directives).  LIST+
  2089.        and LIST- directives that are within included files only affect
  2090.        those files, so you could, for instance, place a LIST- at the
  2091.        start of a source file to be included and just have the listing of
  2092.        that file suppressed.  LIST+ and LIST- directives are useful for
  2093.        selectively listing isolated sections of the source code.
  2094.  
  2095.        See Assembly Listing.
  2096.  
  2097.          ;turn list off, NOP's are not listed
  2098.           List-
  2099.           Nop
  2100.           Nop
  2101.          ;turn list on, NOP's are listed
  2102.           List+
  2103.           Nop
  2104.           Nop
  2105.  
  2106.        ******************************************************************
  2107.  
  2108.        MACRO [parameter, ...]
  2109.  
  2110.        Macro declaration.
  2111.  
  2112.        Begins a macro declaration that will be finished by the ENDM
  2113.        directive.
  2114.  
  2115.        MACRO may have up to ten operands.  These operands must be unique
  2116.        symbols within the macro declaration.  The operands become the
  2117.        names of any parameters passed to the macro upon invocation.  A
  2118.        symbol declaration to name the macro is also required.
  2119.  
  2120.        See Macros.
  2121.  
  2122.          ;defines the macro LOAD_DS, the MACRO
  2123.          ;directive starts the declaration
  2124.  
  2125.          Load_DS Macro Op1
  2126.           Mov Ax, Op1
  2127.           Mov Ds, Ax
  2128.           Endm
  2129.  
  2130.        ******************************************************************
  2131.  
  2132.        MACROC [parameter, ...]
  2133.  
  2134.        Conditional macro declaration.
  2135.  
  2136.        Begins a conditional macro declaration that will be finished by
  2137.        the ENDM directive.
  2138.  
  2139.  
  2140.        48                                             Assembly Directives
  2141.  
  2142.        MACROC may have up to ten operands.  These operands must be unique
  2143.        symbols within the macro declaration.  The operands become the
  2144.        names of any parameters passed to the macro upon invocation.  A
  2145.        symbol declaration to name the macro is also required.
  2146.  
  2147.        See Conditional Macros.
  2148.  
  2149.          ;defines a conditional directive TOO_SMALL
  2150.          ;that is false if the operand is above ten,
  2151.          ;i.e. "if not above ten then do the following"
  2152.  
  2153.          Too_Small Macroc Op1
  2154.           Ifn Op1 > 10
  2155.           Endm
  2156.  
  2157.          ;with the above declaration, the ADD AX,AX
  2158.          ;will be assembled because 11 is above 10
  2159.           Too_Small 11
  2160.            Sub Ax, Ax
  2161.           Else
  2162.            Add Ax, Ax
  2163.           Endif
  2164.  
  2165.        ******************************************************************
  2166.  
  2167.        NEXTIF condition
  2168.  
  2169.        Conditional "if", same level.
  2170.  
  2171.        Finishes the present conditional block and starts a new one.
  2172.        Assembles the following source code only if the condition is true.
  2173.  
  2174.        NEXTIF requires a single immediate data operand.  This operand is
  2175.        the condition to test.
  2176.  
  2177.        See Conditional Assembly.
  2178.  
  2179.          ;any or all of the following may be true:
  2180.          ;if OPTION is equal to ten, CALL SUBRT1 is
  2181.          ;assembled; if OPTION is less than ten,
  2182.          ;CALL SUBRT2 is assembled; if OPTION is greater
  2183.          ;than ten, CALL SUBRT3 is assembled
  2184.           If Option=10
  2185.            Call Subrt1
  2186.           Nextif Option<10
  2187.            Call Subrt2
  2188.           Nextif Option>10
  2189.            Call Subrt3
  2190.           Endif
  2191.  
  2192.  
  2193.        Assembly Directives                                             49
  2194.  
  2195.        ******************************************************************
  2196.  
  2197.        ORG value
  2198.  
  2199.        Origin.
  2200.  
  2201.        Sets the location counter to the specified value.
  2202.  
  2203.        ORG requires a single immediate data operand.  This operand
  2204.        becomes the new location counter value.  If the operand is signed,
  2205.        the value is treated as a displacement to the present location.
  2206.  
  2207.        The default is 100H, which is the starting offset required for COM
  2208.        programs.  ORG affects the location assigned to labels.  ORG can
  2209.        be used to set the offset of specially defined labels.
  2210.  
  2211.          ;this declares three consecutive memory labels, note
  2212.          ;that these declarations only create the labels and do
  2213.          ;not allow space for them in the object code, this sort
  2214.          ;of thing could be done at the end of the program to
  2215.          ;create uninitialized data locations in memory
  2216.  
  2217.          Data1 Label Word
  2218.             Org $+2
  2219.          Data2 Label Word
  2220.             Org $+2
  2221.          Data3 Label Word
  2222.             Org $+2
  2223.  
  2224.          ;remember that signed numbers are treated as displacements
  2225.  
  2226.             Org 2      ;(unsigned, absolute)
  2227.          Symbol1       ;this symbol points to [0002]
  2228.             Org +2     ;(signed, displacement)
  2229.          Symbol2       ;this symbol points to [0004], two past the
  2230.                        ;location above
  2231.  
  2232.        ******************************************************************
  2233.  
  2234.        PAGE [page|subtitle]
  2235.        PAGE page [, subtitle]
  2236.  
  2237.        New page.
  2238.  
  2239.        Starts a new list page regardless of whether paging is on or off,
  2240.        or what the size of the previous page was.
  2241.  
  2242.        PAGE may have none, one, or two operands.  If the first operand is
  2243.        immediate data, it becomes the new page number.  If the first
  2244.        operand a string, it becomes the new page subtitle.  If both a
  2245.        page number and a subtitle are included, the page number must come
  2246.        first.
  2247.  
  2248.  
  2249.        50                                             Assembly Directives
  2250.  
  2251.        If the page number is not specified, the previous page number is
  2252.        incremented.  If the subtitle is not included, the subtitle from
  2253.        the previous page is used.  PAGE can be used in conjunction with
  2254.        automatic paging (PAGE+) to start a new section of the code with a
  2255.        new subtitle.
  2256.  
  2257.        See Assembly Listing.
  2258.  
  2259.          ;start a new page and set the page number
  2260.          ;to ten and the subtitle to "Page ten"
  2261.           Page 10, 'Page ten'
  2262.  
  2263.        ******************************************************************
  2264.  
  2265.        PAGE+ [page|subtitle]
  2266.        PAGE+ page [, subtitle]
  2267.        PAGE-
  2268.  
  2269.        Automatic paging.
  2270.  
  2271.        When automatic paging is activated (PAGE+), a new page is started
  2272.        after every number of lines specified by the PAGESIZE directive
  2273.        (default 60).  When automatic paging is not activated (PAGE-), no
  2274.        paging is done, except by the PAGE directive.  PAGE+ automatically
  2275.        starts a new page if there are operands (i.e. a page number,
  2276.        subtitle, or both).
  2277.  
  2278.        PAGE+ has operands identical to those of PAGE, see PAGE above.
  2279.        PAGE- requires no operands.
  2280.  
  2281.        Default is PAGE-.  Paging can make the listing of a program look
  2282.        better if a hard copy is printed out on separate pages.
  2283.  
  2284.        See Assembly Listing.
  2285.  
  2286.          ;activate auto paging, start a new page, and
  2287.          ;set the subtitle to "Start of Paging"
  2288.           Page+ 'Start of Paging'
  2289.  
  2290.        ******************************************************************
  2291.  
  2292.        PAGESIZE lines [, characters ]
  2293.  
  2294.        Page size.
  2295.  
  2296.        Sets the lines per page and the maximum number of characters per
  2297.        line.  The lines per page affect the number lines output before a
  2298.        new page is started when automatic paging (PAGE+) is active.  The
  2299.        characters per line affect the final length of each list line.
  2300.  
  2301.        PAGESIZE may have one or two immediate data operands.  The first
  2302.        operand becomes the number of lines per page.  The second operand
  2303.        is optional and is the number of characters per line.
  2304.  
  2305.  
  2306.        Assembly Directives                                             51
  2307.  
  2308.        The default lines per page is 60.  The default characters per line
  2309.        is 79.  The lines per page must be in the range 15 to 255 and the
  2310.        characters per line must be in the range 45 to 158.  The number of
  2311.        lines per page and the number of characters per line should only
  2312.        be set once in a program.  The number of characters per line can
  2313.        also be set with LINESIZE.
  2314.  
  2315.          ;this makes for very long pages
  2316.           Pagesize 200
  2317.  
  2318.          ;the following two lines would have the same effect,
  2319.           Pagesize ,50   ;note that the first operand is nul
  2320.          ;Linsize 50     ;characters per line should only be set once
  2321.  
  2322.        ******************************************************************
  2323.  
  2324.        PROC type
  2325.  
  2326.        Procedure declaration.
  2327.  
  2328.        Begin a procedure declaration that will be finished by the ENDP
  2329.        directive.
  2330.  
  2331.        PROC requires a single operand.  This operand is NEAR for near
  2332.        procedures and FAR for far procedures.
  2333.  
  2334.        Far procedures should only be used for routines that will be
  2335.        called by other programs or are called indirectly.  Far procedures
  2336.        cannot be called locally via a CALL instruction.  The type of
  2337.        procedure determines how the returns (RET instructions) within the
  2338.        procedure will be encoded.
  2339.  
  2340.        See Procedures.
  2341.  
  2342.          ;the procedure ORRER is defined, the PROC
  2343.          ;directive starts the declaration
  2344.  
  2345.          Orrer Proc Near
  2346.           Or Cx, 10101b
  2347.           Ret
  2348.           Endp
  2349.  
  2350.        ******************************************************************
  2351.  
  2352.        RESETC [count] [,checksum]
  2353.  
  2354.        Reset counter.
  2355.  
  2356.        Resets the counter ($COUNT) and counter checksum ($SUM).
  2357.  
  2358.  
  2359.        52                                             Assembly Directives
  2360.  
  2361.        RESETC may have none, one, or two immediate data operands.  Both
  2362.        operands are optional.  If the first operand is present, it
  2363.        becomes the new count value.  If the second operand is present, it
  2364.        becomes the new checksum value.  If an operand is missing, zero is
  2365.        used.
  2366.  
  2367.        The new values take effect on the line after the RESETC directive.
  2368.        This directive does not affect the program byte count ($SIZE) or
  2369.        checksum ($CHKSUM).
  2370.  
  2371.           Resetc         ;set count and checksum to zero
  2372.           Mov Ax, $Count ;will load zero to AX
  2373.           Resetc ,20     ;default (zero) for count, 20 for checksum
  2374.           Mov Ax, $Sum   ;will load 20 to AX
  2375.  
  2376.        ******************************************************************
  2377.  
  2378.        SUBTITLE subtitle
  2379.  
  2380.        Program subtitle.
  2381.  
  2382.        Defines the page subtitle for all subsequent pages.
  2383.  
  2384.        SUBTITLE requires a single string operand.  The operand becomes
  2385.        the subtitle.
  2386.  
  2387.        Note that SUBTITLE sets the subtitle for all pages following the
  2388.        present one, not the page in which the SUBTITLE directive appears.
  2389.        The PAGE, PAGE+, and TITLE directives can also be used to set the
  2390.        subtitle.
  2391.  
  2392.        See Assembly Listing.
  2393.  
  2394.          ;set the subtitle of the following pages
  2395.          ;to "Input and Output Routines"
  2396.           Subtitle 'Input and Output Routines'
  2397.  
  2398.        ******************************************************************
  2399.  
  2400.        SYMDUMP+
  2401.        SYMDUMP-
  2402.  
  2403.        Symbol table dump.
  2404.  
  2405.        When activated (SYMDUMP+), the symbol table will be displayed at
  2406.        the end of the listing.  When not activated (SYMDUMP-), the symbol
  2407.        table will not be displayed.
  2408.  
  2409.        Requires no operands.
  2410.  
  2411.        The default is SYMDUMP-.  There is only one symbol dump at the end
  2412.        of the program, i.e. there is no reason to turn the symbol table
  2413.        dump on and then turn it off later.
  2414.  
  2415.  
  2416.        Assembly Directives                                             53
  2417.  
  2418.        See Symbol Table Listing.
  2419.  
  2420.          ;enable symbol dump at the end
  2421.          ;of the program
  2422.           Symdump+
  2423.  
  2424.        ******************************************************************
  2425.  
  2426.        TITLE title [,subtitle]
  2427.  
  2428.        Program title.
  2429.  
  2430.        Defines the page title for the entire program listing.  The
  2431.        starting page subtitle may also be specified.
  2432.  
  2433.        TITLE requires one or two operands.  The first operand becomes the
  2434.        program title.  The optional second operand becomes the subtitle.
  2435.        Both operands must be strings.
  2436.  
  2437.        Only one TITLE directive is valid for the entire program.  The
  2438.        TITLE directive is the only way to set the subtitle on the first
  2439.        page header, since SUBTITLE takes effect on the next page
  2440.        following the directive and PAGE and PAGE+ automatically start a
  2441.        new page.
  2442.  
  2443.        See Assembly Listing.
  2444.  
  2445.          ;set the program title to "Holy Cow" and the
  2446.          ;initial subtitle to "Initialize"
  2447.           Title 'Holy Cow', 'Initialize'
  2448.  
  2449.        ******************************************************************
  2450.  
  2451.        UNUSED+
  2452.        UNUSED-
  2453.  
  2454.        Unused symbol flagging.
  2455.  
  2456.        When active (UNUSED+), all symbols that were never accessed will
  2457.        be flagged.  When not active (UNUSED-), unused symbols will not be
  2458.        flagged.
  2459.  
  2460.        Requires no operands.
  2461.  
  2462.        Used to inform the programmer of unnecessary labels, routines,
  2463.        etc.  Unused macro declarations are never flagged.  The default is
  2464.        UNUSED-.
  2465.  
  2466.  
  2467.        54                                             Assembly Directives
  2468.  
  2469.          ;assuming the near labels SYM1 and SYM2 were
  2470.          ;never accessed, SYM1 is flagged and SYM2 isn't
  2471.           Unused-
  2472.          Sym1
  2473.           Unused+
  2474.          Sym2
  2475.  
  2476.        ******************************************************************
  2477.  
  2478.  
  2479.        Functional Operands                                             55
  2480.  
  2481.                                Functional Operands
  2482.  
  2483.        Functional operands modify another operand passed as an argument.
  2484.        Functional operands serve two general purposes: first to change a
  2485.        characteristic of an operand but still use it in more or less the
  2486.        same way, and second to isolate a specific aspect of an operand.
  2487.        All functional operands take another operand as an argument and
  2488.        can be used anywhere in place of a normal operand.
  2489.  
  2490.        The major categories of functional operands are those that set the
  2491.        size of its argument (ANYSIZE, BYTE, DWORD, QWORD, TBYTE, WORD),
  2492.        those that change the type of its argument (FAR, NEAR), those that
  2493.        change the value of its argument (NEG, NOT), and those that are
  2494.        used to access specific qualities of its argument (OFFSET, SIZE,
  2495.        TYPE, VALUE).
  2496.  
  2497.        ******************************************************************
  2498.  
  2499.        ANYSIZE
  2500.  
  2501.        Size any.
  2502.  
  2503.        Set the size of its argument to all allowable sizes.
  2504.  
  2505.        Its argument must be a memory operand or immediate data.  Can also
  2506.        be used with the LABEL directive.
  2507.  
  2508.          ;the following two statements do not
  2509.          ;conflict because of the ANYSIZE below
  2510.           Mov Bx, Data   ;move 16 bits
  2511.           Add Data, Al   ;add 8 bits
  2512.  
  2513.          Data Label Anysize   ;data label
  2514.           Dw ?                ;declare space for data
  2515.  
  2516.        ******************************************************************
  2517.  
  2518.        BYTE
  2519.  
  2520.        Size byte.
  2521.  
  2522.        Set the size of its argument to byte size (8 bit).
  2523.  
  2524.        Its argument must be a memory operand or immediate data.  Can also
  2525.        be used with the LABEL directive.  Used mainly to declare the
  2526.        number of bits acted upon in an operation if the operation would
  2527.        be ambiguous otherwise.
  2528.  
  2529.          ;the size of [SI] would be ambiguous
  2530.           Mov Byte [Si], 0   ;perform an 8 bit move
  2531.  
  2532.  
  2533.        56                                             Functional Operands
  2534.  
  2535.        ******************************************************************
  2536.  
  2537.        DWORD
  2538.  
  2539.        Size double word.
  2540.  
  2541.        Set the size of its argument to double word size (32 bit).
  2542.  
  2543.        Its argument must be a memory operand or immediate data.  Can also
  2544.        be used with the LABEL directive.  Used mainly to declare the
  2545.        number of bits acted upon in an operation if the operation would
  2546.        be ambiguous otherwise.
  2547.  
  2548.          ;make an intersegment call
  2549.           Call Routine_Location  ;call routine
  2550.  
  2551.          Routine_Location Label Dword   ;the location is 367A:6374
  2552.           Dw 06374h   ;offset
  2553.           Dw 0367ah   ;segment
  2554.  
  2555.        ******************************************************************
  2556.  
  2557.        FAR
  2558.  
  2559.        Type far label.
  2560.  
  2561.        Set the type of its argument to far label.
  2562.  
  2563.        Its argument must be a near label, far label, or memory operand.
  2564.        If its argument is a near or far label, the label is simply
  2565.        converted to a far label.  If its argument is a memory operand,
  2566.        FAR has the same effect as the DWORD function.  This allows FAR to
  2567.        be used in specifying indirect intersegment branching.  FAR is
  2568.        mainly used to declare a far procedure.
  2569.  
  2570.          ;execute an intersegment call, [BX] must point to a location
  2571.          ;containing the segment and offset of the subroutine to execute
  2572.           Call Far [Bx] ;transfer control to routine
  2573.  
  2574.          ;declare a rather insignificant far procedure, cannot
  2575.          ;be called directly, but may be an interrupt handler
  2576.  
  2577.          Subrt Proc Far  ;make far procedure
  2578.           Ret            ;return, don't do anything
  2579.           Endp           ;end of declaration
  2580.  
  2581.        ******************************************************************
  2582.  
  2583.        NEAR
  2584.  
  2585.        Type near label.
  2586.  
  2587.        Set the type of its argument to near label.
  2588.  
  2589.  
  2590.        Functional Operands                                             57
  2591.  
  2592.        Its argument must be a near label, far label, memory operand, or
  2593.        immediate data.  If its argument is a near or far label or
  2594.        immediate data, the operand is simply converted to a near label.
  2595.        If its argument is a memory operand, NEAR has the same effect as
  2596.        the WORD function.  This allows NEAR to be used in specifying
  2597.        indirect same segment branching.  NEAR is mainly used to declare a
  2598.        near procedure.
  2599.  
  2600.          ;execute a same segment call, DATA must point to a location
  2601.          ;containing the offset of the subroutine to execute
  2602.           Call Near Data ;transfer control to routine
  2603.  
  2604.          Data Ds 2       ;two bytes of storage (offset)
  2605.  
  2606.          ;declare a near procedure that doubles AX
  2607.  
  2608.          Double Proc Near ;make near procedure
  2609.           Sal Ax          ;double AX
  2610.           Ret             ;return
  2611.           Endp            ;end of procedure
  2612.  
  2613.          ;NEAR can be used to jump to a literal location
  2614.           Jmp Near 100h  ;branch to start of program
  2615.  
  2616.        ******************************************************************
  2617.  
  2618.        NEG
  2619.  
  2620.        Negate value.
  2621.  
  2622.        Perform an arithmetic negate on the value of its argument.
  2623.  
  2624.        Its argument must be immediate data.  Acts the same as a preceding
  2625.        sign, except that the validity of the result is not checked.
  2626.  
  2627.          ;the following two statements produce the same code
  2628.           Mov Dx, Neg 1 ;load minus one
  2629.           Mov Dx, -1    ;load minus one
  2630.  
  2631.          ;the following statement is really an undetected error
  2632.           Mov Dx, Neg 40000 ;-40000 cannot be represented with 16 bits
  2633.  
  2634.        ******************************************************************
  2635.  
  2636.        NOT
  2637.  
  2638.        Logical not of value.
  2639.  
  2640.        Perform a logical not on the value of its argument.
  2641.  
  2642.  
  2643.        58                                             Functional Operands
  2644.  
  2645.        Its argument must be immediate data.
  2646.  
  2647.          ;the following two statements produce the same code
  2648.           Mov Dh, Not 10101010b  ;load 55H
  2649.           Mov Dh, 01010101b      ;load 55H
  2650.  
  2651.        ******************************************************************
  2652.  
  2653.        OFFSET
  2654.  
  2655.        Offset of label.
  2656.  
  2657.        Return the offset of its argument.
  2658.  
  2659.        Its argument must be a near, far, or memory label.  The offset, or
  2660.        location, is returned as 16 bit immediate data.  Is mainly used by
  2661.        sections of code or individual routines which access data that may
  2662.        be any length (like strings of characters).
  2663.  
  2664.          ;put message location in SI
  2665.           Mov Si, Offset Start               ;location
  2666.          ;put message length in CX
  2667.           Mov Cx, Offset End - Offset Start  ;size
  2668.  
  2669.          Start Db 'This is the message'      ;message data
  2670.          End                                 ;end of message marker
  2671.  
  2672.        ******************************************************************
  2673.  
  2674.        QWORD
  2675.  
  2676.        Size quadruple word.
  2677.  
  2678.        Set the size of its argument to quadruple word (64 bit).
  2679.  
  2680.        Its argument must be a memory operand.
  2681.  
  2682.        ******************************************************************
  2683.  
  2684.        SIZE
  2685.  
  2686.        Size of operand.
  2687.  
  2688.        Return the size of its argument.
  2689.  
  2690.        Its argument may be anything.  The size is returned as 16 bit
  2691.        immediate data for comparison with the size of other operands.
  2692.        See Conditional Operand Testing.
  2693.  
  2694.          ;the NOP is assembled if the sizes are identical
  2695.           If Size Ax = Size Symbol ;compare sizes
  2696.            Nop                ;code if true
  2697.           Endif               ;end of conditional
  2698.  
  2699.  
  2700.        Functional Operands                                             59
  2701.  
  2702.        ******************************************************************
  2703.  
  2704.        TBYTE
  2705.  
  2706.        Size ten byte.
  2707.  
  2708.        Set the size of its argument to ten bytes (80 bit).
  2709.  
  2710.        Its argument must be a memory operand.
  2711.  
  2712.        ******************************************************************
  2713.  
  2714.        TYPE
  2715.  
  2716.        Type of operand.
  2717.  
  2718.        Return the type of its argument.
  2719.  
  2720.        Its argument may be anything.  The type is returned as 16 bit
  2721.        immediate data for comparison with the type of other operands.
  2722.        See Conditional Operand Testing.
  2723.  
  2724.          ;the NOP is assembled if the types are identical
  2725.           If Type Ax = Type Symbol ;compare types
  2726.            Nop                ;code if true
  2727.           Endif               ;end of conditional
  2728.  
  2729.        ******************************************************************
  2730.  
  2731.        WORD
  2732.  
  2733.        Size word.
  2734.  
  2735.        Set the size of its argument to word (16 bit).
  2736.  
  2737.        Its argument must be a memory operand or immediate data.  Can also
  2738.        be used with the LABEL directive.  Used mainly to declare the
  2739.        number of bits acted upon in an operation if the operation would
  2740.        be ambiguous otherwise.
  2741.  
  2742.          ;the size of [BX+SI-10] would be ambiguous
  2743.           Mov Word [Bx+Si-10], 0   ;perform a 16 bit move
  2744.  
  2745.        ******************************************************************
  2746.  
  2747.        VALUE
  2748.  
  2749.        Value of operand.
  2750.  
  2751.        Return the value of its argument.
  2752.  
  2753.  
  2754.        60                                             Functional Operands
  2755.  
  2756.        Its argument may be anything.  The value is returned as 16 bit
  2757.        immediate data for comparison with the value of other operands.
  2758.        See Conditional Operand Testing.
  2759.  
  2760.          ;the NOP is assembled if the values are identical
  2761.           If Value Ax = Value Symbol ;compare sizes
  2762.            Nop                ;code if true
  2763.           Endif               ;end of conditional
  2764.  
  2765.        ******************************************************************
  2766.  
  2767.  
  2768.        Assembly Constants                                              61
  2769.  
  2770.                                Assembly Constants
  2771.  
  2772.        Assembly constants are special symbols that are interpreted into
  2773.        immediate data during assembly.  Assembly constants may be used
  2774.        anywhere in place of immediate data.  Beware that these constants
  2775.        can cause an otherwise unexplained phase errors when used with
  2776.        instructions that directly manipulate the the location counter,
  2777.        like ORG.  Care should also be taken when using assembly constants
  2778.        with assembly directives that must control the assembly based on a
  2779.        value. Assembly constants may always be safely used as operands
  2780.        for 8086 instructions and in byte and word declarations (DB and
  2781.        DW).
  2782.  
  2783.        All symbols starting with a dollar sign are reserved as assembly
  2784.        constants.
  2785.  
  2786.        ******************************************************************
  2787.  
  2788.        $
  2789.  
  2790.        Present location.
  2791.  
  2792.        Returns the present value of the location counter.  Same as $LOC.
  2793.        May be safely used with the ORG directive.  16 bit.
  2794.  
  2795.          ;declares two memory labels that are ten bytes from each other
  2796.  
  2797.          Data_Area1 Label Byte   ;first label
  2798.                     Org $ + 10   ;advance location counter
  2799.          Data_Area2 Label Byte   ;second label
  2800.  
  2801.        ******************************************************************
  2802.  
  2803.        $CHKSUM
  2804.  
  2805.        Program checksum.
  2806.  
  2807.        Returns the byte checksum of the object code up to and including
  2808.        the previous source line.  8 bit.
  2809.  
  2810.        ******************************************************************
  2811.  
  2812.        $COUNT
  2813.  
  2814.        Byte count.
  2815.  
  2816.        Returns the number of bytes of code since the beginning of the
  2817.        program or the last RESETC directive.  16 bit.
  2818.  
  2819.  
  2820.        62                                              Assembly Constants
  2821.  
  2822.          ;branch around the string and then load its size
  2823.           Jmps Continue                  ;skip string
  2824.           Resetc                         ;reset counter
  2825.           Db 'Which way did he go?'      ;string declaration
  2826.          Continue                        ;continue execution
  2827.           Mov Cx, $Count                 ;load byte count
  2828.  
  2829.        ******************************************************************
  2830.  
  2831.        $DATE1
  2832.  
  2833.        Month and day.
  2834.  
  2835.        Returns the present day and month in the system format.  The high
  2836.        byte is the month (1 to 12) and the low byte is the day (1 to 31).
  2837.        16 bit.
  2838.  
  2839.        ******************************************************************
  2840.  
  2841.        $DATE2
  2842.  
  2843.        Year.
  2844.  
  2845.        Returns the present year in the system format.  The value is 1980
  2846.        to 2099.  16 bit.
  2847.  
  2848.        ******************************************************************
  2849.  
  2850.        $END
  2851.  
  2852.        End of program.
  2853.  
  2854.        Returns the last location counter value of the program.  If no ORG
  2855.        statments have been used, it will return the same thing as $SIZE +
  2856.        100H.  Is useful in adjusting the memory allocation.
  2857.  
  2858.         ;reduce memory allocation to minimum, assume ES=SS=CS
  2859.           Mov Ah, 4ah          ;function number
  2860.           Mov Bx, $END         ;end of code and data
  2861.           Mov Sp, Bx           ;set stack
  2862.           Shr Bx
  2863.           Shr Bx
  2864.           Shr Bx
  2865.           Shr Bx               ;make paragraph form, BX/16
  2866.           Inc Bx               ;round up
  2867.           Int 21h              ;execute
  2868.  
  2869.           :                    ;all code and data
  2870.  
  2871.           Org +100h            ;make room for stack
  2872.          ;<-- this is the location that $END will return.
  2873.  
  2874.  
  2875.        Assembly Constants                                              63
  2876.  
  2877.        ******************************************************************
  2878.  
  2879.        $LOC
  2880.  
  2881.        Present location.
  2882.  
  2883.        Returns the present value of the location counter.  Same as $.
  2884.        May be safely used with the ORG directive.
  2885.  
  2886.        ******************************************************************
  2887.  
  2888.        $SIZE
  2889.  
  2890.        Program size.
  2891.  
  2892.        Returns the total size of the assembled program in bytes.  16 bit.
  2893.  
  2894.          ;load the size of the program into AX
  2895.           Mov Ax, $Size  ;load size
  2896.  
  2897.        ******************************************************************
  2898.  
  2899.        $SUM
  2900.  
  2901.        Counter checksum.
  2902.  
  2903.        Returns the byte checksum of the object code up to and including
  2904.        the previous source line since the beginning of the program or the
  2905.        last RESETC.  8 bit.
  2906.  
  2907.        ******************************************************************
  2908.  
  2909.        $TIME1
  2910.  
  2911.        Second and 1/100 second.
  2912.  
  2913.        Returns the present second and 1/100 second in the system format.
  2914.        The high byte is the second (0 to 59) and the low byte is the
  2915.        1/100 second (0 to 99).  16 bit.
  2916.  
  2917.        ******************************************************************
  2918.  
  2919.        $TIME2
  2920.  
  2921.        Hour and minute.
  2922.  
  2923.        Returns the present hour and minute in the system format.  The
  2924.        high byte is the hour (0 to 23) and the low byte is the minute (0
  2925.        to 59).  16 bit.
  2926.  
  2927.  
  2928.        64                                              Assembly Constants
  2929.  
  2930.        ******************************************************************
  2931.  
  2932.        $VERSION
  2933.  
  2934.        Assembler version.
  2935.  
  2936.        Returns the version number of the assembler.  The high byte is the
  2937.        minor version number and the low byte is the major version number.
  2938.  
  2939.          ;if assembling with WASM 2.14, AL get 2 and AH gets 14
  2940.           Mov Ax, $Version
  2941.  
  2942.        ******************************************************************
  2943.  
  2944.  
  2945.        Reserved Symbols                                                65
  2946.  
  2947.                                 Reserved Symbols
  2948.  
  2949.        The following are guidelines for what not to use as symbols.  All
  2950.        of these symbols have special meaning to WASM:
  2951.  
  2952.          AX      AL      ES       BYTE      OR
  2953.          CX      CL      CS       WORD      AND
  2954.          DX      DL      SS       DWORD     XOR
  2955.          BX      BL      DS       QWORD     MOD
  2956.          SP      AH      NOT      TBYTE     SIZE
  2957.          BP      CH      OFFSET   ANYSIZE   TYPE
  2958.          SI      DH      NEAR     ST        VALUE
  2959.          DI      BH      FAR      NEG
  2960.  
  2961.        A single question mark is also a reserved symbol.  All fields
  2962.        beginning with 0 to 9 are reserved for numbers.  All fields
  2963.        starting with a dollar sign ($) are reserved for assembly
  2964.        constants.  The following characters should never be used in
  2965.        symbols: control characters (ASCII 0 to 31), spaces, commas; and
  2966.        also any of the following: ; + - * = ' / \ ( ) < > [ ]  Macros
  2967.        should be unique from all other instructions, rather than the
  2968.        special symbols above.  It is recommended that programmer defined
  2969.        symbols start with a letter and consist of only letters, numbers,
  2970.        and underscores.
  2971.  
  2972.        66                                                Assembly Listing
  2973.  
  2974.                                 Assembly Listing
  2975.  
  2976.        The assembly listing is a comprehensive trace of the assembly and
  2977.        can be useful in debugging or making a hard copy of a program.  A
  2978.        listing is only generated if a list file is specified.  The
  2979.        assembly is speeded up if no list is generated.  A listing can be
  2980.        started or stopped with LIST+ and LIST- (these directives are
  2981.        ignored if no list file is specified).  The listing of macro
  2982.        expansion lines can be enabled with EXPAND+ (the default), or
  2983.        disabled with the EXPAND-.  Also a listing of the symbol table
  2984.        will be generated if a SYMDUMP+ is included somewhere in the
  2985.        program (see Symbol Table Listing).
  2986.  
  2987.        List directives within an included file only apply to the listing
  2988.        of that file, and expand directives within a macro only apply to
  2989.        the expansion of that macro.  This means you can place a LIST- at
  2990.        the start of an included file to suppress the listing of just that
  2991.        file. You can use an EXPAND- similarly to create a macro that is
  2992.        never expanded.
  2993.  
  2994.        The listing may be divided up into pages.  An individual page can
  2995.        be started with PAGE.  Automatic paging can be turned on with
  2996.        PAGE+ and turned off with PAGE- (the default).  The default page
  2997.        size is 60 lines (which includes a five line page header).  The
  2998.        page size can be modified with PAGESIZE.
  2999.  
  3000.        Each list page starts with a formfeed (ASCII 12) and a list
  3001.        header.  The formfeed is not included on the first page or on any
  3002.        pages of a listing sent to CON.  The list header consists of a
  3003.        programmer defined title and subtitle, the name of the main source
  3004.        file, the page number, the time and date, columnar headings for
  3005.        the list lines, and the assembler version.
  3006.  
  3007.        The title and subtitle are left justified in lines one and two
  3008.        respectively.  Only one title applies for an entire assembly
  3009.        listing.  Both the title and subtitle can be set with TITLE.  The
  3010.        subtitle can also be set with SUBTITLE, PAGE, and PAGE+.
  3011.  
  3012.        The source file name is displayed with the present page number,
  3013.        separated by a pair of dashes, right justified on the first line
  3014.        (opposite to the title).  Only the main source file name is
  3015.        displayed (never any included file names).  The page number starts
  3016.        at one and increments with each page.  The page number is never
  3017.        directly based on the pages within a source file (unlike list line
  3018.        numbers).  The page number can be set with PAGE and PAGE+.
  3019.  
  3020.        The time and date are right justified on the second line (opposite
  3021.        to the subtitle).
  3022.  
  3023.  
  3024.        Assembly Listing                                                67
  3025.  
  3026.        The columnar headings and the assembler version follow a blank
  3027.        line after the first two lines of the header (they are on line
  3028.        four).  In the columnar list headings: Loc stands for location
  3029.        counter, Obj stands for object code, Line stands for line number,
  3030.        and Source stands for source code.  The assembler version is
  3031.        justified to the right of the headings.
  3032.  
  3033.        The listing starts after another blank line (i.e. the sixth line
  3034.        of the page).  Each list line contains the location counter value
  3035.        (in hex), the object code for that line (also in hex), the source
  3036.        line number, a special indicator byte, and the source line itself.
  3037.  
  3038.        The location counter is not displayed if the line is blank or the
  3039.        location is not relevant to the instruction contained in that
  3040.        source line.
  3041.  
  3042.        No object code will be displayed if, of course, none is generated
  3043.        by the source line.  Some instructions (DS) never display their
  3044.        object code.  Procedure (PROC) and End-Procedure (ENDP) directives
  3045.        display the present procedure nest level instead.  Macros display
  3046.        the present macro nest level.
  3047.  
  3048.        The line number is always the actual line number within the source
  3049.        file.  Included source files maintain their own line numbering.
  3050.        You can use this number in your text editor to locate the line
  3051.        within its file.  Since macro expansion lines are not in the
  3052.        source file, no line number is displayed.
  3053.  
  3054.        The special indicator byte is a plus (+) for macro expansion
  3055.        lines, a minus (-) for included source files, and is blank
  3056.        otherwise.
  3057.  
  3058.        The source line is converted to upper-case (except for strings and
  3059.        comments), and will be truncated if necessary to make the entire
  3060.        list line the proper width.  The default width is 79.  The width
  3061.        can be modified with LINESIZE and PAGESIZE.  The LINESIZE
  3062.        directive can also be used to send special codes to your printer
  3063.        (with the purpose of setting a font).
  3064.  
  3065.        All the assembly directives mentioned in this description can be
  3066.        looked up under Assembly Directives.
  3067.  
  3068.  
  3069.        68                                            Symbol Table Listing
  3070.  
  3071.                               Symbol Table Listing
  3072.  
  3073.        A symbol table listing can be activated with SYMDUMP+.  The symbol
  3074.        table is listed at the very end of the assembly.  All symbols in
  3075.        the program are included, except symbols within macro expansions
  3076.        or declarations, and symbols that were defined in code that was
  3077.        skipped due to conditional assembly.
  3078.  
  3079.        The symbol table listing is divided five parts: Branch Locations,
  3080.        Memory References, Equated Values, Defined Macros, and Undefined
  3081.        Symbols.  Each section starts a new page.  The titles describing
  3082.        the section replace the normal columnar headings.
  3083.  
  3084.        The symbols are sorted alphabetically within each section.  For
  3085.        the purposes of alphabetization, underscores are ignored, for
  3086.        example: the symbol A_B carries the same weight as AB, both of
  3087.        these symbols would come after AA and before AC.  If a value is
  3088.        displayed with the symbol, it will be lined up to the right,
  3089.        expressed in hex.
  3090.  
  3091.        The branch locations section lists all the branch labels (types
  3092.        NEAR and FAR) within the program, including the names of
  3093.        procedures (which are just near labels).  Each symbol is
  3094.        accompanied by the location it represents.
  3095.  
  3096.        The memory reference section lists all the memory reference labels
  3097.        (type BYTE, WORD, etc.) within the program.  Each symbol is
  3098.        accompanied by the location it represents.
  3099.  
  3100.        The equated values section lists all the symbols defined by the
  3101.        EQU directive.  Each symbol is accompanied by the value it
  3102.        represents.
  3103.  
  3104.        The defined macros section lists all the macros that where defined
  3105.        within the program.  Every macro that was defined will be listed,
  3106.        whether or not it was used.
  3107.  
  3108.        The undefined symbols section lists all symbols that were used but
  3109.        not defined.
  3110.  
  3111.  
  3112.        Assembly Messages                                               69
  3113.  
  3114.                                 Assembly Messages
  3115.  
  3116.        The integrity of the source code is constantly checked during
  3117.        assembly.  Lines containing errors will be flagged with an
  3118.        appropriate error message.  Some lines are only flagged with a
  3119.        comment.  A comment is more of an observation than an error.
  3120.        Comments try to provide useful advice about the assembly.
  3121.        Comments are not included in the error count displayed at the end
  3122.        of assembly.
  3123.  
  3124.        Error and comment messages will be sent to the list file if a
  3125.        listing is being generated, otherwise the message will be
  3126.        displayed to the screen followed by the source line that caused
  3127.        the error or comment.  A line may be flagged with more than one
  3128.        message.  Paging occurs indiscriminately, so that error or comment
  3129.        messages may not appear on the same page as the line that they are
  3130.        flagging.
  3131.  
  3132.        Error messages start with "- - - Error: " and comment messages
  3133.        start with "- - - Comment: ".  Many error and comment messages are
  3134.        followed on the same line by sections of the source code or
  3135.        numbers.  Numbers will either be decimal or hexadecimal (followed
  3136.        by an "H").  If a line is flagged in an included file, the name of
  3137.        the file will appear in parenthesis following the message.  If a
  3138.        line is flagged in a macro expansion, the last source line number
  3139.        will appear in parenthesis.  If both of these conditions are true,
  3140.        then both the file name and line number will appear.
  3141.  
  3142.        Many times the thing that caused one error will cause others, so
  3143.        fixing up one error will often clear up others.  If the reasons
  3144.        for a particular error are unclear, try solving any previous
  3145.        errors first.
  3146.  
  3147.        Some errors may terminate the assembly.  If this happens, the
  3148.        message ">>>Cannot Continue<<<" will be displayed to the screen
  3149.        and the speaker will be sounded.
  3150.  
  3151.        Several assembly directives allow control over error flagging and
  3152.        detection.  The flagging of every undefined symbol occurrence can
  3153.        be activated or deactivated with FLAGALL+ and FLAGALL-; the
  3154.        detection of possible short unconditional jumps may be activated
  3155.        or deactivated with JUMP+ and JUMP-; and the flagging of unused
  3156.        symbols may be activated or deactivated with UNUSED+ and UNUSED-.
  3157.        A programmer defined error may be created with ERROR.  Finally,
  3158.        the maximum number of errors detected before the assembly is
  3159.        terminated can be controlled with ERRORMAX.  See Assembly
  3160.        Directives for more information on these directives.
  3161.  
  3162.  
  3163.        70                                               Assembly Messages
  3164.  
  3165.        The following is a description of all assembly messages:
  3166.  
  3167.        Address error
  3168.          There is some kind of error in an indirect memory operand.
  3169.          Probably an illegal combination of addressing registers.  The
  3170.          legal addressing register combinations are: BX, BP, DI, SI,
  3171.          BX+DI, BX+SI, BP+DI, and BP+SI.  Any of these combinations may
  3172.          also include an immediate data offset or displacement.
  3173.  
  3174.        Ambiguous memory reference
  3175.          A memory operand does not have its size properly specified.
  3176.          Usually occurs when the operands are a memory operand and
  3177.          immediate data and the size of the first is not defined.  Under
  3178.          those circumstances, the size of the memory operand should be
  3179.          defined with an explicit BYTE or WORD function.  This error also
  3180.          occurs if a LABEL directive is missing its operand.
  3181.  
  3182.        Cannot create list file: <file name>
  3183.          The list file could not be created or opened.  Probably because
  3184.          of an invalid file name.  The name of the list file is
  3185.          displayed.  Refer to the DOS manual for a description of legal
  3186.          file names.  Critical error.
  3187.  
  3188.        Cannot create object file: <file name>
  3189.          The object file could not be created or opened.  Probably
  3190.          because of an invalid file name.  The name of the object file is
  3191.          displayed.  Refer to the DOS manual for a description of legal
  3192.          file names.  Critical error.
  3193.  
  3194.        Could use JMPS: <displacement>
  3195.          The branch location is close enough so that a short
  3196.          unconditional jump (JMPS) instruction could be substituted for a
  3197.          normal jump (JMP).  The only effect this change would have is to
  3198.          shorten the resulting object code by one byte, i.e. the code is
  3199.          not incorrect the way it stands.  The flagging of possible short
  3200.          jumps is enabled with the JUMP+ directive.
  3201.  
  3202.        Data too long in declaration: <operand value>
  3203.          The initialization value (the second operand) of the DS
  3204.          directive is more than eight bits.  The value is displayed, it
  3205.          should be in the range 0 to 255.
  3206.  
  3207.        Disk full or write error: <file name>
  3208.          An error occurred in writing to the object or list file.
  3209.          Probably because the disk is full.  The name of the file in
  3210.          which the error occurred is displayed.  Make sure that the disk
  3211.          has enough free space, or send the object file or listing to
  3212.          another disk or device.  Critical error.
  3213.  
  3214.        Division by zero
  3215.          A division by zero occurred somewhere in an operand expression.
  3216.          The The value of the divisor must be changed to something other
  3217.          than zero.
  3218.  
  3219.  
  3220.        Assembly Messages                                               71
  3221.  
  3222.        Duplicate definition: <symbol>
  3223.          A symbol was declared more than once.  In addition to normal
  3224.          symbol declarations at the start of source lines, the parameter
  3225.          names after a MACRO directive are also considered symbol
  3226.          declarations (though only local to that macro).  Every duplicate
  3227.          definition of a symbol is flagged.  The symbol declarations must
  3228.          be changed so that they are all unique.  The symbol is
  3229.          displayed.
  3230.  
  3231.        ENDM without MACRO
  3232.          An ENDM directive was found without a corresponding MACRO or
  3233.          MACROC.
  3234.  
  3235.        ENDP without PROC
  3236.          An ENDP directive was found without a corresponding PROC.
  3237.  
  3238.        EQU without symbol
  3239.          The EQU directive was used without a symbol declaration.  An
  3240.          equate is meaningless without a symbol, thus a symbol
  3241.          declaration is required.
  3242.  
  3243.        IF statements nested too deeply: <maximum nest level>
  3244.          Conditional IF or IFN directives were nested too deeply.  The
  3245.          maximum nest level is displayed.
  3246.  
  3247.        Illegal addressing operand: <operand>
  3248.          An operand within brackets is not a valid addressing operand.
  3249.          The valid addressing operands are BX, BP, DI, SI, memory labels,
  3250.          and immediate data.  The operand is displayed.
  3251.  
  3252.        Illegal argument for ANYSIZE: <argument>
  3253.          The argument given for ANYSIZE is not valid.  The argument
  3254.          should be immediate data or a memory operand.  The argument is
  3255.          displayed.
  3256.  
  3257.        Illegal argument for BYTE: <argument>
  3258.          The argument given for BYTE is not valid.  The argument should
  3259.          be immediate data or a memory operand.  The argument is
  3260.          displayed.
  3261.  
  3262.        Illegal argument for DWORD: <argument>
  3263.          The argument given for DWORD is not valid.  The argument should
  3264.          be immediate data or a memory operand.  The argument is
  3265.          displayed.
  3266.  
  3267.        Illegal argument for FAR:
  3268.          The argument given for FAR is not valid.  The argument should be
  3269.          a near label, far label, or memory operand.  The argument is
  3270.          displayed.
  3271.  
  3272.        Illegal argument for NEAR: <argument>
  3273.          The argument given for NEAR is not valid.  The argument should
  3274.          be a near label, far label, memory operand, or immediate data.
  3275.          The argument is displayed.
  3276.  
  3277.  
  3278.        72                                               Assembly Messages
  3279.  
  3280.        Illegal argument for NEG: <argument>
  3281.          The argument given for NEG is not valid.  The argument should be
  3282.          immediate data.  The argument is displayed.
  3283.  
  3284.        Illegal argument for NOT: <argument>
  3285.          The argument given for NOT is not valid.  The argument should be
  3286.          immediate data.  The argument is displayed.
  3287.  
  3288.        Illegal argument for OFFSET: <argument>
  3289.          The argument given for OFFSET is not valid.  The argument should
  3290.          be a near label, far label, or memory label.  The argument is
  3291.          displayed.
  3292.  
  3293.        Illegal argument for QWORD: <argument>
  3294.          The argument given for QWORD is not valid.  The argument should
  3295.          be a memory operand.  The argument is displayed.
  3296.  
  3297.        Illegal argument for ST: <argument>
  3298.          The argument given for ST is not valid.  The argument should be
  3299.          immediate data.
  3300.  
  3301.        Illegal argument for TBYTE: <argument>
  3302.          The argument given for TBYTE is not valid.  The argument should
  3303.          be a memory operand.  The argument is displayed.
  3304.  
  3305.        Illegal argument for WORD: <argument>
  3306.          The argument given for WORD is not valid.  The argument should
  3307.          be immediate data or a memory operand.  The argument is
  3308.          displayed.
  3309.  
  3310.        Illegal number or symbol: <operand field>: <illegal character>
  3311.          An operand field started with a numerical digit (0 to 9), thus
  3312.          is interpreted as a number, but has an illegal character in it.
  3313.          Usually is a result of leaving the "H" off the end of
  3314.          hexadecimal numbers.  May also be the result of using a symbol
  3315.          that was inadvertently declared with a digit as its first
  3316.          character.  The operand field and the illegal character within
  3317.          it are displayed.
  3318.  
  3319.        Illegal operand in declaration: <operand>
  3320.          An operand in a DB or DW directive is invalid.  All DB operands
  3321.          must be immediate data or strings.  All DW operands must be
  3322.          immediate data.  The operand is displayed.
  3323.  
  3324.  
  3325.        Assembly Messages                                               73
  3326.  
  3327.        Illegal operand(s): <first type> <second type>
  3328.          One or both of the operands given for the instruction are
  3329.          not valid.  The first two operand types are displayed.  The
  3330.          valid operands for any given instruction may be looked up under
  3331.          Instruction Set.
  3332.  
  3333.          The following table shows the meaning of the displayed type
  3334.          bits.  Multiple bits may be active, like AX = 0006H (bits one
  3335.          and two):
  3336.  
  3337.          Bit  Operand Type
  3338.          ---  ------------
  3339.            0  no operand
  3340.            1  non-segment register
  3341.            2  accumulator (AX or AL)
  3342.            3  segment register
  3343.            4  memory operand in brackets
  3344.            5  immediate data
  3345.            6  string
  3346.            7  near label
  3347.            8  far label
  3348.            9  memory label
  3349.           10  8087 stack
  3350.           11  8087 stack top
  3351.           12  signed operand
  3352.           13  undefined symbol
  3353.           14  (internal use)
  3354.           15  (internal use)
  3355.  
  3356.        Illegal operator or symbol: <operator>
  3357.          One of the special delimiters was out of place or some sort of
  3358.          broader syntax error occurred in the operands of the
  3359.          instruction.  May be because of an illegal operand expression,
  3360.          like AX+1.  May be because of an extra operator, like 1+++1.
  3361.          May be because of a generally illegal construct, like (1+) or
  3362.          [OFFSET].  May be because of an illegal operator within a memory
  3363.          operand, like [5*3] or [1-BX].  May be because of illegal
  3364.          operators in the parameter names after the MACRO directive, like
  3365.          A+B.  The illegal character (operator) is displayed.  The
  3366.          operators AND, OR, XOR, and MOD will only show up as A, O, X,
  3367.          and \.
  3368.  
  3369.        Illegal printer code: <operand>
  3370.          A printer code following the LINESIZE directive is not valid.
  3371.          The printer codes must be 8 bit immediate data.
  3372.  
  3373.        Illegal reference: <value>
  3374.          The value of an equate changed during assembly and is thus not
  3375.          valid.  Probably because a changeable assembly constant was
  3376.          used, or the equate referenced an operand with OFFSET in it
  3377.          before the OFFSET argument was defined, or the equate referenced
  3378.          another, not yet defined equate.  The initial value of the
  3379.          equate is displayed.
  3380.  
  3381.  
  3382.        74                                               Assembly Messages
  3383.  
  3384.        Illegal use of MACRO symbol: <symbol>
  3385.          A macro symbol was used as an operand.  Macros may only be used
  3386.          as instructions.  The symbol is displayed.
  3387.  
  3388.        INCLUDE file not found: <file name>
  3389.          The include file could not be found or opened.  Probably because
  3390.          of an incorrect file name.  Make sure that all components of the
  3391.          file name are correct.  Remember that the source drive/path and
  3392.          an extension of ASM are assumed if not otherwise specified.  The
  3393.          name of the include file is displayed.
  3394.  
  3395.        INCLUDE's nested too deeply
  3396.          An INCLUDE directive inside of an included file was encountered.
  3397.          Include files may not be nested.
  3398.  
  3399.        INCLUDE within macro
  3400.          An INCLUDE directive inside of a macro expansion was detected.
  3401.          INCLUDE's may not be placed in macros.
  3402.  
  3403.        Invalid character in symbol: <symbol>
  3404.          The symbol being declared contains invalid character(s).
  3405.          Presently all symbols with a first character of "0" through "9"
  3406.          (reserved for numbers) or a first character of "$" (reserved for
  3407.          assembly constants) are flagged.  Macro parameter names
  3408.          (following a MACRO directive) can also be flagged in a similar
  3409.          manner.  The symbol must be changed so it conforms to the legal
  3410.          format.  The symbol is displayed.  See Reserved Symbols.
  3411.  
  3412.        Invalid operand size: <first size> <second size>
  3413.          No version of the instruction was found with matching operand
  3414.          sizes. This comment is provided to assist in fixing an Invalid
  3415.          Operands error.  The size of the first two operands are
  3416.          displayed. The valid operands and sizes for any given
  3417.          instruction may be looked up under Instruction Set.
  3418.  
  3419.          The following table shows the meaning of the displayed size
  3420.          bits.  Multiple bits may be active, like 5 = 0003H (bits zero
  3421.          and one):
  3422.  
  3423.          Bit  Operand Size
  3424.          ---  ------------
  3425.           0   8 bits, byte
  3426.           1   16 bits, word
  3427.           2   32 bits, double word
  3428.           3   64 bits, quadruple word
  3429.           4   80 bits, ten byte
  3430.  
  3431.          Bits 5 through 15 are for internal use.
  3432.  
  3433.        LABEL without label
  3434.          The LABEL directive was used without a symbol declaration.  A
  3435.          label declaration is meaningless without a symbol, thus a symbol
  3436.          is required.
  3437.  
  3438.  
  3439.        Assembly Messages                                               75
  3440.  
  3441.        Line size out of range: <specified size>
  3442.          The length of the line specified by a LINESIZE or PAGESIZE
  3443.          directive is either too small or too large.  The value must be
  3444.          in the range 45 to 158.  The value is displayed.
  3445.  
  3446.        MACRO without symbol
  3447.          The MACRO directive was used without a symbol declaration.  A
  3448.          macro declaration is meaningless without a symbol, thus a symbol
  3449.          is required.
  3450.  
  3451.        Macros nested too deeply: <maximum nest level>
  3452.          Macros are being expanded too deeply.  The maximum nest level is
  3453.          displayed.
  3454.  
  3455.        Missing ENDIF: <number>
  3456.          At least one ENDIF directive was found to be missing when the
  3457.          end of the source code was reached.  The number of missing
  3458.          ENDIF's are displayed.
  3459.  
  3460.        Missing ENDM
  3461.          An ENDM directive was found without a corresponding MACRO.
  3462.  
  3463.        Missing ENDP: <number>
  3464.          At least one ENDP directive was found to be missing when the end
  3465.          of the program was reached.  Since specific PROC's are not
  3466.          matched to specific ENDP's, the actual error may exist anywhere
  3467.          in the program, even though it isn't detected until the end of
  3468.          the program.  The number of missing ENDP's are displayed.
  3469.  
  3470.        Missing IF
  3471.          A NEXTIF, ELSEIF, ELSE, or ENDIF directive was found without a
  3472.          corresponding IF or IFN.  All conditional sections of source
  3473.          code must start with an IF or IFN.
  3474.  
  3475.        Missing or illegal operator: <field>
  3476.          Two fields were found not separated by a comma or valid
  3477.          operator.  Individual components of an operand expression must
  3478.          be separated by some kind of operator.  The individual operands
  3479.          of an instruction must be separated by commas.  Something like a
  3480.          misspelled AND operator could cause this error.  The second of
  3481.          the two fields are displayed.
  3482.  
  3483.        Missing PROC
  3484.          A RET instruction was found outside of a procedure.  Since the
  3485.          RET instruction needs a PROC directive to set the type of
  3486.          return, all RET's must fall within a procedure.  Near and far
  3487.          returns can be encoded independent of procedure definitions with
  3488.          RETN and RETF.
  3489.  
  3490.        Missing right bracket
  3491.          A memory operand using brackets came to an end without a right
  3492.          bracket (via an end of line or comma).  May occur because of a
  3493.          general error in syntax, like [OFFSET], where the bracket is
  3494.          passed to the OFFSET function as an argument and is overlooked.
  3495.  
  3496.  
  3497.        76                                               Assembly Messages
  3498.  
  3499.        Operand cannot be combined: <operand>
  3500.          The operand may not be used in an expression.  The operand is
  3501.          displayed.  Only immediate data may be used in expressions.
  3502.  
  3503.        Operands are incompatible sizes: <first size> <second size>
  3504.          The operands for the instruction are not compatible sizes,
  3505.          though the instruction involves exchanging data between the two.
  3506.          The sizes of the first two operands are displayed.  See the
  3507.          Invalid Operand Size error for a description of the size bits.
  3508.  
  3509.        Out of memory for code table: <maximum lines>
  3510.          The internal code table is full and no more lines can be
  3511.          assembled.  The maximum number of source lines that can be
  3512.          assembled is displayed.  See Memory Limitations.  Critical
  3513.          error.
  3514.  
  3515.        Out of memory for macro table: <bytes available>
  3516.          The internal macro storage area is full and no more macros can
  3517.          be defined.  The total available bytes of macro storage is
  3518.          displayed.  See Memory Limitations.  Critical error.
  3519.  
  3520.        Out of memory for symbol table: <symbol>: <bytes available>
  3521.          The internal symbol table is full and no more symbols may be
  3522.          defined.  The symbol that caused the error and the total
  3523.          available bytes for the symbol table is displayed.  See Memory
  3524.          Limitations.  Critical error.
  3525.  
  3526.        Overflow: <number>
  3527.          A number or the result of an expression is too big or too small.
  3528.          Individual numbers must be in the range 0 to 65535 (unsigned) or
  3529.          +32767 to -32768 (signed).  If any single value in an expression
  3530.          is signed, the entire expression is considered signed.  The
  3531.          final result of an expression must fall in the same unsigned or
  3532.          signed ranges as individual numbers.  If the error occurs
  3533.          because of an individual number, the number will be displayed.
  3534.  
  3535.        Page size out of range: <specified size>
  3536.          The length of the page specified by a PAGESIZE directive is
  3537.          either too small or too large.  The value must be in the range
  3538.          15 to 255. The value is displayed.
  3539.  
  3540.        Parenthesis nested too deeply
  3541.          The parenthesis in an operand expression were nested too deeply.
  3542.          Parenthesis may only be nested ten deep.
  3543.  
  3544.        Parenthetical error
  3545.          There was some kind of error in an operand expression involving
  3546.          parenthesis, like ((1).
  3547.  
  3548.  
  3549.        Assembly Messages                                               77
  3550.  
  3551.        Phase error: <previous value>
  3552.          The location counter somehow became out of phase with previous
  3553.          assembly passes.  The error may be occurring sometime previous
  3554.          to its detection, since the phase is only checked for symbol
  3555.          declarations (only labels).  This error probably means that the
  3556.          source code was assembled differently in different passes.
  3557.          Could be caused by something like conditionally assembling a
  3558.          section of the code based on the one of the time constants (like
  3559.          $TIME1), which may be different each pass.  Could also be caused
  3560.          by directly manipulating the location counter in an unsound
  3561.          fashion, like using assembly constants (which aren't really very
  3562.          constant) to set the location counter.  The previous location
  3563.          counter value is displayed.
  3564.  
  3565.        Procedures nested too deeply: <maximum nest level>
  3566.          Procedure declarations are nested too deeply.  The maximum nest
  3567.          level is displayed.
  3568.  
  3569.        Register size override: <first size> <second size>
  3570.          The size of the register is not compatible with the size of the
  3571.          memory operand.  The size of the memory operand may explicitly
  3572.          changed with a BYTE or WORD function.  The sizes of the first
  3573.          two operands are displayed.  See the Invalid Operand Size error
  3574.          for a description of the size bits.  This message doesn't
  3575.          necessarily indicate an error, but merely acts as a warning.
  3576.  
  3577.        Should be byte data
  3578.          The immediate data operand (port number) of an IN or OUT
  3579.          instruction is not eight bits.
  3580.  
  3581.        Source file not found: <file name>
  3582.          The source file could not be found or opened.  Probably because
  3583.          of an incorrectly typed file name.  Make sure that all
  3584.          components of the file name are correct.  Remember that the
  3585.          default drive/path and an extension of ASM are assumed if not
  3586.          otherwise specified.  The name of the source file is displayed.
  3587.          Critical error.
  3588.  
  3589.        Source line too long: <excess>
  3590.          The line within a macro expansion would be too long if all the
  3591.          parameters in that line were inserted.  The parameters or the
  3592.          line itself must be shortened.  The approximate amount by which
  3593.          the line is too long by is displayed.
  3594.  
  3595.        String not closed
  3596.          A string field was started with a single quote but not closed by
  3597.          a matching one.  A matching single quote must be added.
  3598.  
  3599.  
  3600.        78                                               Assembly Messages
  3601.  
  3602.        Too far for short jump: <displacement>
  3603.          The target of the branch is not close enough for a short jump
  3604.          (its displacement should be in the range +127 to -128, or 007F
  3605.          to FF80 hex).  If the instruction is a JMPS, then JMP may be
  3606.          used instead.  If the instruction is one of the conditional
  3607.          branches, the source code must be moved around so that target is
  3608.          closer, or a combination of conditional and unconditional
  3609.          branching must be used.  The present displacement is displayed.
  3610.  
  3611.            ;you could change the following ...
  3612.             Jz Toofar    ;TOOFAR is too far for a short jump
  3613.  
  3614.            ;... to the following
  3615.             Jnz Skipjump ;skip long jump on opposite condition
  3616.             Jmp Toofar   ;long jump to TOOFAR
  3617.            Skipjump
  3618.  
  3619.        Too many MACRO parameters: <maximum parameters>
  3620.          Too many parameters are being passed to the macro upon
  3621.          invocation.  The maximum number of parameters is not determined
  3622.          by the number specified in the macro declaration, but rather is
  3623.          based on internal memory constraints.  The number of parameters
  3624.          must be reduced.  The maximum allowed parameters are displayed.
  3625.  
  3626.        Undefined assembly directive: <number>
  3627.          Should not get this error.  It means that the instruction is an
  3628.          assembly directive that is not fully defined.
  3629.  
  3630.        Undefined error
  3631.          Should not get this error.  It means that an undefined error
  3632.          occurred.
  3633.  
  3634.        Undefined symbol: <symbol>
  3635.          The symbol was used but not defined anywhere.  Might be because
  3636.          the first digit of a hexadecimal number was not 0 through 9.
  3637.          This error can be enabled for all subsequent occurrences of
  3638.          the symbol with the FLAGALL+ directive.
  3639.  
  3640.        Unrecognized instruction: <mnemonic>
  3641.          The instruction mnemonic was not recognized.  It is not an 8086
  3642.          instruction, assembly directive, or a macro.  The mnemonic is
  3643.          displayed.
  3644.  
  3645.        Unused symbol: <symbol>
  3646.          The declared symbol was never used.  This message does not
  3647.          indicate an error, but rather assists in "cleaning up" the
  3648.          source code.  The detection of unused symbols enabled is enabled
  3649.          with the UNUSED+ directive.
  3650.  
  3651.        WASM detects checksum failure
  3652.          The copy of WASM.COM is corrupted and cannot be used.  If you
  3653.          don't know why you're getting this message, try making a new
  3654.          working copy from your master disk or the original archive file.
  3655.  
  3656.  
  3657.        Assembly Messages                                               79
  3658.  
  3659.        WASM detects incorrect DOS version
  3660.          The operating system is pre-2.0.  WASM requires PC or MS DOS 2.0
  3661.          or greater to function.
  3662.  
  3663.        WASM detects insufficient memory
  3664.          There is not enough free memory for WASM to function.  Though
  3665.          your computer may have enough memory installed, device drivers
  3666.          and memory resident programs could be using too much.  See
  3667.          Memory Limitations.
  3668.  
  3669.        80                                                 Instruction Set
  3670.  
  3671.                                  Instruction Set
  3672.  
  3673.        This is a brief list of all the legal predefined instructions and
  3674.        their operand types.  The instructions are divided up by function.
  3675.        The groups are: assembly directives, data transfer, arithmetic,
  3676.        logic, flag setting, control transfer, string manipulation, and
  3677.        processor control, 8087 Data Transfer, 8087 Arithmetic, 8087
  3678.        Transcendental, 8087 Constants, 8087 Flag Setting, 8087 Processor
  3679.        Control.  The assembly directives are more thoroughly described
  3680.        under Assembly Directives.  The 8086 and 8087 instructions are not
  3681.        thoroughly described in this documentation, you'll need another
  3682.        source for that.
  3683.  
  3684.        Instruction Format:
  3685.  
  3686.          <mnemonic> = <short description>
  3687.            <operand> [, <operand>, ...] [=<comment>]
  3688.  
  3689.        Operand Types:
  3690.  
  3691.          none     no operands
  3692.          reg      register (non-segment)
  3693.          seg      segment register
  3694.          accum    AX or AL
  3695.          mem      memory operand
  3696.          immed    immediate data
  3697.          stack    8087 stack operand
  3698.          near     near label
  3699.          string   string data
  3700.          symbol   a unique symbol
  3701.  
  3702.        Operands separated by slashes mean that either one may be used.
  3703.        Operands in capital letters are the literal operands accepted.
  3704.        Operands in brackets are optional, all others are required.
  3705.  
  3706.        Numbers in parenthesis indicate the allowable size (number of
  3707.        bits) for the specified operands.  If no size is given then the
  3708.        operands may be either 8 or 16 bit (where applicable).
  3709.  
  3710.        All 8087 instructions begin with F, while integer forms of
  3711.        instructions begin with FI, BCD forms begin with FB, and no-wait
  3712.        form begin with FN.  Instructions that pop the stack upon
  3713.        completion end with a P.  Instructions that reverse the order of
  3714.        operation (source <op> destination, instead of destination <op>
  3715.        source) end with an R.  Instructions that both pop and reverse end
  3716.        with an RP.  Instructions that encode without a wait begin with
  3717.        FN.
  3718.  
  3719.        ******************************************************************
  3720.  
  3721.                                Assembly Directives
  3722.  
  3723.        DB = declare bytes
  3724.          immed/string [, immed/string, ...]
  3725.  
  3726.  
  3727.        Instruction Set                                                 81
  3728.  
  3729.        DS = declare storage
  3730.          immed [, immed(8)] = bytes, value (default 0)
  3731.  
  3732.        DW = declare words
  3733.          immed [, immed, ...]
  3734.  
  3735.        ELSE = conditional "else"
  3736.          immed
  3737.  
  3738.        ELSEIF = conditional "else-if"
  3739.          immed
  3740.  
  3741.        ENDIF = end of conditional statement
  3742.          none
  3743.  
  3744.        ENDM = end of macro declaration
  3745.          none
  3746.  
  3747.        ENDP = end of procedure
  3748.          none
  3749.  
  3750.        EQU = equate, requires label
  3751.          immed
  3752.  
  3753.        ERROR = programmer defined error
  3754.          string = error message
  3755.  
  3756.        EXPAND+ = list macro expansions (default)
  3757.          none
  3758.  
  3759.        EXPAND- = do not list macro expansions
  3760.          none
  3761.  
  3762.        ERRORMAX = set maximum errors (default 65535)
  3763.          immed
  3764.  
  3765.        FLAGALL+ = flag all occurrences of undefined symbols
  3766.          none
  3767.  
  3768.        FLAGALL- = flag only first occurrence of undef. symbols (default)
  3769.          none
  3770.  
  3771.        IF = conditional "if"
  3772.          immed
  3773.  
  3774.        IFN = conditional "if not"
  3775.          immed
  3776.  
  3777.        INCLUDE = include source file
  3778.          string = file name (default source drive and ext)
  3779.  
  3780.        JUMP+ = flag long jumps that could be short
  3781.          none
  3782.  
  3783.  
  3784.        82                                                 Instruction Set
  3785.  
  3786.        JUMP- = do not flag long jumps that could be short (default)
  3787.          none
  3788.  
  3789.        LABEL = define label, requires label
  3790.          NEAR/FAR/BYTE/WORD/DWORD/QWORD/TBYTE/ANYSIZE
  3791.  
  3792.        LINESIZE = set page width (default 79)
  3793.          [immed] [, immed(8), ...] = page width, printer codes
  3794.  
  3795.        LIST+ = generate listing (default if list file specified)
  3796.          none
  3797.  
  3798.        LIST- = list output off
  3799.          none
  3800.  
  3801.        MACRO = start of macro declaration
  3802.          [symbol, ...] = parameter names
  3803.  
  3804.        MACROC = start of conditional macro declaration
  3805.          [symbol, ...] = parameter names
  3806.  
  3807.        NEXTIF = conditional "if", same level
  3808.          immed
  3809.  
  3810.        ORG = origin (default 100H)
  3811.          immed = relative to location if signed
  3812.  
  3813.        PAGE = start new page
  3814.          [immed/string]  = page number, subtitle
  3815.          immed [, string] = page number, subtitle
  3816.  
  3817.        PAGE+ = start auto paging
  3818.          [immed/string]  = page number, subtitle
  3819.          immed [, string] = page number, subtitle
  3820.  
  3821.        PAGE- = stop auto paging (default)
  3822.          none
  3823.  
  3824.        PAGESIZE = set page size (default 60,79)
  3825.          immed [,immed] = page length, page width
  3826.  
  3827.        PROC = beginning of procedure
  3828.          NEAR/FAR
  3829.  
  3830.        RESETC = reset byte counter
  3831.         [immed] [,immed] = counter value, checksum value (default 0, 0)
  3832.  
  3833.        SUBTITLE = set program subtitle
  3834.          string = subtitle
  3835.  
  3836.        SYMDUMP+ = symbol table dump on
  3837.          none
  3838.  
  3839.  
  3840.        Instruction Set                                                 83
  3841.  
  3842.        SYMDUMP- = symbol table dump off (default)
  3843.          none
  3844.  
  3845.        TITLE = set program title
  3846.          string [, string] = title, subtitle
  3847.  
  3848.        UNUSED+ = flag unused symbols
  3849.          none
  3850.  
  3851.        UNUSED- = do not flag unused symbols (default)
  3852.          none
  3853.  
  3854.        ******************************************************************
  3855.  
  3856.                                   Data Transfer
  3857.  
  3858.        IN = input
  3859.          accum, immed(8) = input from a fixed port
  3860.          accum, DX = input from a variable port in DX
  3861.  
  3862.        LAHF = load AH with flags
  3863.          none
  3864.  
  3865.        LDS = load DS and register
  3866.          reg(16), reg/mem
  3867.  
  3868.        LEA = load effective address
  3869.          reg(16), reg/mem
  3870.  
  3871.        LES = load ES and register
  3872.          reg(16), reg/mem
  3873.  
  3874.        MOV = move
  3875.          reg/mem, reg/seg
  3876.          reg/seg, reg/mem
  3877.          reg/mem, immed
  3878.  
  3879.        OUT = output
  3880.          immed(8), accum = output to fixed port
  3881.          DX, accum = output to variable port in DX
  3882.  
  3883.        POP = pop (16)
  3884.          reg/seg/mem
  3885.  
  3886.        POPF = pop flags
  3887.          none
  3888.  
  3889.        PUSH = push (16)
  3890.          reg/seg/mem
  3891.  
  3892.        PUSHF = pop flags
  3893.          none
  3894.  
  3895.  
  3896.        84                                                 Instruction Set
  3897.  
  3898.        SAHF = store AH to flags
  3899.          none
  3900.  
  3901.        XCHG = exchange
  3902.          reg/mem, reg
  3903.          reg, reg/mem
  3904.  
  3905.        XLAT = translate byte in AL
  3906.          none
  3907.  
  3908.        ******************************************************************
  3909.  
  3910.                                    Arithmetic
  3911.  
  3912.        AAA = ASCII adjust for add
  3913.          none
  3914.  
  3915.        AAD = ASCII adjust for divide
  3916.          none
  3917.  
  3918.        AAM = ASCII adjust for multiply
  3919.          none
  3920.  
  3921.        AAS =  ASCII adjust for subtract
  3922.          none
  3923.  
  3924.        ADC = add with carry
  3925.          reg/mem, reg
  3926.          reg, reg/mem
  3927.          reg/mem, immed
  3928.  
  3929.        ADD = add
  3930.          reg/mem, reg
  3931.          reg, reg/mem
  3932.          reg/mem, immed
  3933.  
  3934.        CBW = convert byte to word
  3935.          none
  3936.  
  3937.        CWD = convert word to double word
  3938.          none
  3939.  
  3940.        DAA = decimal adjust for add
  3941.          none
  3942.  
  3943.        DAS = decimal adjust for subtract
  3944.          none
  3945.  
  3946.        DEC = decrement
  3947.          reg/mem
  3948.  
  3949.        DIV = divide, unsigned
  3950.          [accum,] reg/mem = accum implicit
  3951.  
  3952.  
  3953.        Instruction Set                                                 85
  3954.  
  3955.        IDIV = integer divide, signed
  3956.          [accum,] reg/mem = accum implicit
  3957.  
  3958.        IMUL = integer multiply, signed
  3959.          [accum,] reg/mem = accum implicit
  3960.  
  3961.        INC = increment
  3962.          reg/mem
  3963.  
  3964.        MUL = multiply, unsigned
  3965.          [accum,] reg/mem = accum implicit
  3966.  
  3967.        NEG = decrement
  3968.          reg/mem
  3969.  
  3970.        SBB = subtract with borrow
  3971.          reg/mem, reg
  3972.          reg, reg/mem
  3973.          reg/mem, immed
  3974.  
  3975.        SUB = subtract
  3976.          reg/mem, reg
  3977.          reg, reg/mem,
  3978.          reg/mem, immed
  3979.  
  3980.  
  3981.        ******************************************************************
  3982.  
  3983.                                       Logic
  3984.  
  3985.        AND = and
  3986.          reg/mem, reg
  3987.          reg, reg/mem
  3988.          reg/mem, immed
  3989.  
  3990.        NOT = not
  3991.          reg/mem
  3992.  
  3993.        OR = or
  3994.          reg/mem, reg
  3995.          reg, reg/mem
  3996.          reg/mem, immed
  3997.  
  3998.        RCL = rotate through carry left
  3999.          reg/mem = one time
  4000.          reg/mem, CL = CL times
  4001.  
  4002.        RCR = rotate through carry right
  4003.          reg/mem = one time
  4004.          reg/mem, CL = CL times
  4005.  
  4006.        ROL = rotate left
  4007.          reg/mem = one time
  4008.          reg/mem, CL = CL times
  4009.  
  4010.  
  4011.        86                                                 Instruction Set
  4012.  
  4013.        ROR = rotate right
  4014.          reg/mem = one time
  4015.          reg/mem, CL = CL times
  4016.  
  4017.        SAL = shift arithmetic left
  4018.          reg/mem = one time
  4019.          reg/mem, CL = CL times
  4020.  
  4021.        SAR = shift arithmetic right
  4022.          reg/mem = one time
  4023.          reg/mem, CL = CL times
  4024.  
  4025.        SHL = shift logical left
  4026.          reg/mem = one time
  4027.          reg/mem, CL = CL times
  4028.  
  4029.        SHR = shift logical right
  4030.          reg/mem = one time
  4031.          reg/mem, CL = CL times
  4032.  
  4033.        XOR = xor
  4034.          reg/mem, reg
  4035.          reg, reg/mem
  4036.          reg/mem, immed
  4037.  
  4038.        ******************************************************************
  4039.  
  4040.                                   Flag Setting
  4041.  
  4042.        CLC = clear carry
  4043.          none
  4044.  
  4045.        CLD = clear direction
  4046.          none
  4047.  
  4048.        CLI = clear interrupt
  4049.          none
  4050.  
  4051.        CMC = clear complement carry
  4052.          none
  4053.  
  4054.        CMP = compare
  4055.          reg/mem, reg
  4056.          reg, reg/mem
  4057.          reg/mem, immed
  4058.  
  4059.        STC = set carry
  4060.          none
  4061.  
  4062.        STD = set direction
  4063.          none
  4064.  
  4065.        STI = set interrupt
  4066.          none
  4067.  
  4068.  
  4069.        Instruction Set                                                 87
  4070.  
  4071.        TEST = test
  4072.          reg/mem, reg
  4073.          reg, reg/mem
  4074.          reg/mem, immed
  4075.  
  4076.        ******************************************************************
  4077.  
  4078.                                 Control Transfer
  4079.  
  4080.        CALL = call
  4081.          near = direct within segment
  4082.          immed (offset), immed (segment) = direct intersegment
  4083.          reg/mem = indirect within segment (16)
  4084.          mem = indirect intersegment (32)
  4085.  
  4086.        INT = interrupt
  4087.          immed(8)
  4088.  
  4089.        INT3 = type 3 interrupt
  4090.          none
  4091.  
  4092.        INTO = interrupt on overflow
  4093.          none
  4094.  
  4095.        IRET =interrupt return
  4096.          none
  4097.  
  4098.        JA = jump if above
  4099.          near
  4100.  
  4101.        JAE = jump if above or equal
  4102.          near
  4103.  
  4104.        JB = jump if below
  4105.          near
  4106.  
  4107.        JBE = jump if below or equal
  4108.          near
  4109.  
  4110.        JC = jump if carry
  4111.          near
  4112.  
  4113.        JCXZ = jump if CX equal to zero
  4114.          near
  4115.  
  4116.        JE = jump if equal
  4117.          near
  4118.  
  4119.        JG = jump if greater
  4120.          near
  4121.  
  4122.        JGE = jump if greater or equal
  4123.          near
  4124.  
  4125.  
  4126.        88                                                 Instruction Set
  4127.  
  4128.        JL = jump if less
  4129.          near
  4130.  
  4131.        JLE = jump if less or equal
  4132.          near
  4133.  
  4134.        JMP = unconditional jump
  4135.          near = direct within segment
  4136.          immed (offset), immed (segment) = direct intersegment
  4137.          reg/mem = indirect within segment (16)
  4138.          mem = indirect intersegment (32)
  4139.  
  4140.        JMPS = unconditional short jump
  4141.          near
  4142.  
  4143.        JNA = jump if not above
  4144.          near
  4145.  
  4146.        JNAE = jump if not above or equal
  4147.          near
  4148.  
  4149.        JNB = jump if not below
  4150.          near
  4151.  
  4152.        JNBE = jump if not below or equal
  4153.          near
  4154.  
  4155.        JNC = jump if no carry
  4156.          near
  4157.  
  4158.        JNE = jump if not equal
  4159.          near
  4160.  
  4161.        JNG = jump if not greater
  4162.          near
  4163.  
  4164.        JNGE = jump if not greater or equal
  4165.          near
  4166.  
  4167.        JNL = jump if not less
  4168.          near
  4169.  
  4170.        JNLE = jump if not less or equal
  4171.          near
  4172.  
  4173.        JNO = jump if not overflow
  4174.          near
  4175.  
  4176.        JNP = jump if not parity
  4177.          near
  4178.  
  4179.        JNS = jump if not sign
  4180.          near
  4181.  
  4182.  
  4183.        Instruction Set                                                 89
  4184.  
  4185.        JNZ = jump if not zero
  4186.          near
  4187.  
  4188.        JO = jump if overflow
  4189.          near
  4190.  
  4191.        JP = jump if parity
  4192.          near
  4193.  
  4194.        JPE = jump if parity even
  4195.          near
  4196.  
  4197.        JPO = jump if parity odd
  4198.          near
  4199.  
  4200.        JS = jump if sign
  4201.          near
  4202.  
  4203.        JZ = jump if zero
  4204.          near
  4205.  
  4206.        LOOP = loop CX times
  4207.          near
  4208.  
  4209.        LOOPE = loop while equal
  4210.          near
  4211.  
  4212.        LOOPNE = loop while not equal
  4213.          near
  4214.  
  4215.        LOOPNZ = loop while not zero
  4216.          near
  4217.  
  4218.        LOOPZ = loop while zero
  4219.          near
  4220.  
  4221.        RET = return, type determined by procedure
  4222.          none
  4223.          immed = add immed to stack
  4224.  
  4225.        RETF = within segment return
  4226.          none
  4227.          immed = add immed to stack
  4228.  
  4229.        RETN = intersegment return
  4230.          none
  4231.          immed = add immed to stack
  4232.  
  4233.        ******************************************************************
  4234.  
  4235.                                String Manipulation
  4236.  
  4237.        CMPSB = compare string byte
  4238.          none
  4239.  
  4240.  
  4241.        90                                                 Instruction Set
  4242.  
  4243.        CMPSW = compare string word
  4244.          none
  4245.  
  4246.        LODSB = load string byte
  4247.          none
  4248.  
  4249.        LODSW = load string word
  4250.          none
  4251.  
  4252.        MOVSB = move string byte
  4253.          none
  4254.  
  4255.        MOVSW = move string word
  4256.          none
  4257.  
  4258.        REP = repeat CX times
  4259.          none
  4260.  
  4261.        REPE = repeat while equal
  4262.          none
  4263.  
  4264.        REPNE = repeat while not equal
  4265.          none
  4266.  
  4267.        REPNZ = repeat while not zero
  4268.          none
  4269.  
  4270.        REPZ = repeat while zero
  4271.          none
  4272.  
  4273.        SCASB = scan string byte
  4274.          none
  4275.  
  4276.        SCASW = scan string word
  4277.          none
  4278.  
  4279.        STOSB = store string byte
  4280.          none
  4281.  
  4282.        STOSW = store string word
  4283.          none
  4284.  
  4285.        ******************************************************************
  4286.  
  4287.                                 Processor Control
  4288.  
  4289.        CS: = code segment override prefix
  4290.          none
  4291.  
  4292.        DS: = data segment override prefix
  4293.          none
  4294.  
  4295.        ES: = extra segment override prefix
  4296.          none
  4297.  
  4298.  
  4299.        Instruction Set                                                 91
  4300.  
  4301.        HLT = halt
  4302.          none
  4303.  
  4304.        LOCK = bus lock prefix
  4305.          none
  4306.  
  4307.        NOP = no operation
  4308.          none
  4309.  
  4310.        SEG = segment override prefix (same effect as CS:, DS:, etc.)
  4311.          seg
  4312.  
  4313.        SS: = stack segment override prefix
  4314.          none
  4315.  
  4316.        WAIT = wait
  4317.          none
  4318.  
  4319.        ******************************************************************
  4320.  
  4321.                                8087 Data Transfer
  4322.  
  4323.        FLD = load to real to ST
  4324.          none = FLD ST, ST(1)
  4325.          [ST,] stack
  4326.          [ST,] mem(32,64,80)
  4327.  
  4328.        FILD = load integer to ST
  4329.          [ST,] mem(16,32,64)
  4330.  
  4331.        FBLD = load BCD to ST
  4332.          [ST,] mem(80)
  4333.  
  4334.        FST = store ST to real
  4335.          none = FST ST(1), ST
  4336.          stack [,ST]
  4337.          mem(32,64) [,ST]
  4338.  
  4339.        FIST = store ST to integer
  4340.          mem(16,32) [,ST]
  4341.  
  4342.        FSTP = store ST to real and pop
  4343.          none = FSTP ST(1), ST
  4344.          stack [,ST]
  4345.          mem(32,64,80) [,ST]
  4346.  
  4347.        FISTP = store ST to integer and pop
  4348.          mem(16,32,64) [,ST]
  4349.  
  4350.        FBSTP = store ST to BCD and pop
  4351.          mem(80) [,ST]
  4352.  
  4353.  
  4354.        92                                                 Instruction Set
  4355.  
  4356.        FXCH = exchange
  4357.          none = FXCH ST(1), ST
  4358.          stack [,ST]
  4359.  
  4360.        ******************************************************************
  4361.  
  4362.                                  8087 Arithmetic
  4363.  
  4364.        FADD = add real to ST
  4365.          none = FADDP ST(1), ST
  4366.          stack, ST
  4367.          [ST,] stack
  4368.          [ST,] mem(32,64)
  4369.  
  4370.        FIADD = add integer to ST
  4371.          [ST,] mem(16,32)
  4372.  
  4373.        FADDP = add ST to real and pop
  4374.          none = FADDP ST(1), ST
  4375.          stack [,ST]
  4376.  
  4377.        FABS = absolute value of ST
  4378.          none
  4379.  
  4380.        FCHS = change sign of ST
  4381.          none
  4382.  
  4383.        FDIV = divide ST by real
  4384.          none = FDIVP ST(1), ST
  4385.          stack, ST
  4386.          [ST,] stack
  4387.          [ST,] mem(32,64)
  4388.  
  4389.        FIDIV = divide ST by integer
  4390.          [ST,] mem(16,32)
  4391.  
  4392.        FDIVP = divide ST by real and pop
  4393.          none = FDIVP ST(1), ST
  4394.          stack [,ST]
  4395.  
  4396.        FDIVR = divide real by ST
  4397.          none = FDIVRP ST(1), ST
  4398.          stack, ST
  4399.          [ST,] stack
  4400.          [ST,] mem(32,64)
  4401.  
  4402.        FIDIVR = divide integer by ST
  4403.          [ST,] mem(16,32)
  4404.  
  4405.        FDIVRP = divide real by ST and pop
  4406.          none = FDIVRP ST(1), ST
  4407.          stack [,ST]
  4408.  
  4409.  
  4410.        Instruction Set                                                 93
  4411.  
  4412.        FMUL = multiply real with ST
  4413.          none = FMULP ST(1), ST
  4414.          stack, ST
  4415.          [ST,] stack
  4416.          [ST,] mem(32,64)
  4417.  
  4418.        FIMUL = multiply integer with ST
  4419.          [ST,] mem(16,32)
  4420.  
  4421.        FMULP = multiply real with ST and pop
  4422.          none = FMULP ST(1), ST
  4423.          stack [,ST]
  4424.  
  4425.        FPREM = partial remainder of ST divided by ST(1)
  4426.          none
  4427.  
  4428.        FRNDINT = round ST to integer
  4429.          none
  4430.  
  4431.        FSCALE = scale ST by ST(1)
  4432.          none
  4433.  
  4434.        FSQRT = square root of ST
  4435.          none
  4436.  
  4437.        FSUB = subtract real from ST
  4438.          none = FSUBP ST(1), ST
  4439.          stack, ST
  4440.          [ST,] stack
  4441.          [ST,] mem(32,64)
  4442.  
  4443.        FISUB = subtract integer from ST
  4444.          [ST,] mem(16,32)
  4445.  
  4446.        FSUBP = subtract real from ST and pop
  4447.          none = FSUBP ST(1), ST
  4448.          stack [,ST]
  4449.  
  4450.        FSUBR = subtract ST from real
  4451.          none = FSUBRP ST(1), ST
  4452.          stack, ST
  4453.          [ST,] stack
  4454.          [ST,] mem(32,64)
  4455.  
  4456.        FISUBR = subtract ST from integer
  4457.          [ST,] mem(16,32)
  4458.  
  4459.        FSUBRP = subtract ST from real and pop
  4460.          none = FSUBRP ST(1), ST
  4461.          stack [,ST]
  4462.  
  4463.  
  4464.        94                                                 Instruction Set
  4465.  
  4466.        FXTRACT = extract components of ST
  4467.          none
  4468.  
  4469.        ******************************************************************
  4470.  
  4471.                                8087 Transcendental
  4472.  
  4473.        F2XM1 = [2^ST]-1
  4474.          none
  4475.  
  4476.        FPATAN = partial arctangent of ST divided by ST(1)
  4477.          none
  4478.  
  4479.        FPTAN = partial tangent of ST
  4480.          none
  4481.  
  4482.        FYL2X = ST(1)*[LOG2[ST]]
  4483.          none
  4484.  
  4485.        FYL2XP1 = ST(1)*[LOG2[ST+1]]
  4486.          none
  4487.  
  4488.        ******************************************************************
  4489.  
  4490.                                  8087 Constants
  4491.  
  4492.        FLD1 = load 1.0 into ST
  4493.          none
  4494.  
  4495.        FLDL2E = load log base 2 of e into ST
  4496.          none
  4497.  
  4498.        FLDL2T = load log base 2 of 10 into ST
  4499.          none
  4500.  
  4501.        FLDLG2 = load log base 10 of 2 into ST
  4502.          none
  4503.  
  4504.        FLDLN2 = load log base e of 2 into ST
  4505.          none
  4506.  
  4507.        FLDPI = load pi into ST
  4508.          none
  4509.  
  4510.        FLDZ = load 0 into ST
  4511.          none
  4512.  
  4513.        ******************************************************************
  4514.  
  4515.                                 8087 Flag Setting
  4516.  
  4517.  
  4518.        Instruction Set                                                 95
  4519.  
  4520.        FCOM = compare real to ST
  4521.          none = FCOM ST, ST(1)
  4522.          [ST,] stack
  4523.          [ST,] mem(32,64)
  4524.  
  4525.        FICOM = compare integer to ST
  4526.          [ST,] mem(16,32)
  4527.  
  4528.        FCOMP = compare real to ST and pop
  4529.          none = FCOMP ST, ST(1)
  4530.          [ST,] stack
  4531.          [ST,] mem(32,64)
  4532.  
  4533.        FICOMP = compare integer to ST and pop
  4534.          [ST,] mem(16,32)
  4535.  
  4536.        FCOMPP = compare ST(1) to ST and pop twice
  4537.          none
  4538.  
  4539.        FTST = test ST
  4540.          none
  4541.  
  4542.        FXAM = examine ST
  4543.          none
  4544.  
  4545.        ******************************************************************
  4546.  
  4547.                              8087 Processor Control
  4548.  
  4549.        FCLEX = clear exceptions
  4550.          none
  4551.  
  4552.        FDECSTP = decrement stack pointer
  4553.          none
  4554.  
  4555.        FDISI = disable interrupts
  4556.          none
  4557.  
  4558.        FENI = enable interrupts
  4559.          none
  4560.  
  4561.        FFREE = free ST(i)
  4562.          none
  4563.          stack
  4564.  
  4565.        FINCSTP = increment stack pointer
  4566.          none
  4567.  
  4568.        FINIT = initialize 8087
  4569.          none
  4570.  
  4571.        FLDCW = load control word
  4572.          mem(16)
  4573.  
  4574.  
  4575.        96                                                 Instruction Set
  4576.  
  4577.        FLDENV = load environment
  4578.          mem
  4579.  
  4580.        FNCLEX = clear exceptions, no wait
  4581.          none
  4582.  
  4583.        FNDISI = disable interrupts, no wait
  4584.          none
  4585.  
  4586.        FNENI = enable interrupts, no wait
  4587.          none
  4588.  
  4589.        FNINIT = initialize 8087, no wait
  4590.          none
  4591.  
  4592.        FNOP = no operation
  4593.          none
  4594.  
  4595.        FNSAVE = save state, no wait
  4596.          mem
  4597.  
  4598.        FNSTCW = store control word, no wait
  4599.          mem(16)
  4600.  
  4601.        FNSTENV = store environment, no wait
  4602.          mem
  4603.  
  4604.        FRSTOR = restore state
  4605.          mem
  4606.  
  4607.        FNSTSW = store status word, no wait
  4608.          mem(16)
  4609.  
  4610.        FSAVE = save state
  4611.          mem
  4612.  
  4613.        FSTCW = store control word
  4614.          mem(16)
  4615.  
  4616.        FSTENV = store environment
  4617.          mem
  4618.  
  4619.        FSTSW = store status word
  4620.          mem(16)
  4621.  
  4622.        FWAIT = wait
  4623.          none
  4624.  
  4625.        ******************************************************************
  4626.  
  4627.  
  4628.        8087 Programming                                                97
  4629.  
  4630.                                 8087 Programming
  4631.  
  4632.        The 8087 NDP performs operations with its own internal, 80 bit,
  4633.        floating point registers.  These registers are implemented as a
  4634.        stack.  Operations are carried out by loading the relevant data
  4635.        onto the 8087 stack, executing the operations, and then storing
  4636.        the results back to main memory.
  4637.  
  4638.        Though the 8087 works with and can load very accurate real
  4639.        numbers, WASM can only intialize 8 and 16 bit integers.  There are
  4640.        several ways around this shortcoming:  1. You could load only 16
  4641.        bit integers.  2. You could encode a larger number into words and
  4642.        bytes.  3. You could write a short routine to load numbers.
  4643.  
  4644.          ;load some integers
  4645.           Fild Data1   ;load the 16 bit integer 56
  4646.           Fild Data2   ;load the 64 bit integer 0123456789ABCDEFH
  4647.  
  4648.          Data1 Dw 56           ;16 bit integer
  4649.          Data2 Label Qword     ;64 bit integer
  4650.           Dw 00123h
  4651.           Dw 04567h
  4652.           Dw 089abh
  4653.           Dw 0cdefh
  4654.  
  4655.          ;load a floating point real number
  4656.           Fbld Data3a  ;load 123456780
  4657.           Fild Data3b  ;load 10**4
  4658.           Fld St(0)    ;duplicate
  4659.           Fmul         ;multiply and pop, now have 10**8
  4660.           Fdiv         ;divide and pop, now have 1.23456780
  4661.  
  4662.          Data3a Label Tbyte    ;packed BCD number (low bytes first)
  4663.           Db 80h, 67h, 45h, 23h, 01h, 00h, 00h, 00h, 00h, 00h, 00h
  4664.          Data3b Dw 10000       ;will be the exponent
  4665.  
  4666.        Synchronization between the two processors is achieved with the
  4667.        WAIT instruction.  WASM automatically inserts a WAIT in front of
  4668.        all 8087 instructions.  There are several instructions that may be
  4669.        encoded without the WAIT.  They are: FCLEX, FDISI, FENI, FINIT,
  4670.        FSAVE, FSTCW, FSTENV, and FSTSW.  To encode these instructions
  4671.        without a WAIT, begin the mnemonic with FN, as in FNCLEX, FNDISI,
  4672.        etc.
  4673.  
  4674.        If data written by the 8087 is to be accessed immediately by the
  4675.        8086, an FWAIT must be explicitly encoded.  This forces the 8086
  4676.        to wait until the 8087 has finished writing the data.
  4677.  
  4678.           Fstp Result          ;store result
  4679.           Fwait                ;wait for 8087 to finish
  4680.           Mov Ax, Result       ;load result to AX
  4681.  
  4682.          Result Dw ?
  4683.  
  4684.  
  4685.        98                                            External Subroutines
  4686.  
  4687.                               External Subroutines
  4688.  
  4689.        Programs assembled by WASM may be used as external subroutines by
  4690.        other programs.  A programming language that can call pure binary
  4691.        image, external, machine language subroutines should be able to
  4692.        call programs assembled with WASM.  BASIC and Turbo Pascal are two
  4693.        languages that can do this.  Refer to the BASIC or Pascal manual
  4694.        for the specific implementation.
  4695.  
  4696.        BASIC expects the external machine language subroutine to be in
  4697.        the BLOAD format.  This is easily done adding the proper header to
  4698.        the file, which is as follows:
  4699.  
  4700.          ;this is a BLOAD header, it should
  4701.          ;be the first code in the program
  4702.           Db 0fdh    ;BLOAD marker
  4703.           Dw 0f000H  ;segment to load it at
  4704.           Dw 0       ;offset to load it at
  4705.           Dw $Size   ;size of program
  4706.  
  4707.        The segment and offset of the load can be any number, since it
  4708.        should be specified by the programmer when loading it from BASIC.
  4709.        Making load address F000:0000 (which is read only memory) will
  4710.        prevent loading it over something important if the address is not
  4711.        specified.
  4712.  
  4713.        Turbo Pascal external subroutines do not require any special
  4714.        format.
  4715.  
  4716.        The code within Turbol Pascal subroutines must be relocatable.
  4717.        This means that no references to the location counter should be
  4718.        made (the location is undefined).  Since memory labels cannot be
  4719.        used, there is no good way to access declared local data; its
  4720.        probably better to just do without such data.  BASIC subroutines
  4721.        may or may not have to be relocatable, depending upon where they
  4722.        are stored.  If the address is known beforehand (in an unused
  4723.        screen buffer for instance), the code need not be relocatable and
  4724.        the starting offset will be known and can be set with ORG.  If the
  4725.        BASIC subroutine is stored in a variable's data space or a file
  4726.        buffer, then the code must be relocatable.
  4727.  
  4728.        Machine language subroutines may be debugged by placing an INT3
  4729.        instruction within the code and then running the entire program
  4730.        (BASIC or Pascal) under DEBUG.  When the subroutine is executed,
  4731.        the INT3 will give control to the DEBUG program and allow you to
  4732.        step through your code.  Make sure to remove the INT3 and
  4733.        reassemble the code when you are through debugging.
  4734.  
  4735.        Programs that are assembled as subroutines are not directly
  4736.        executable, thus it may be a wise idea to name them with an
  4737.        extension other than .COM (which implies that a program is
  4738.        executable).
  4739.  
  4740.  
  4741.        Source Code Clarification                                       99
  4742.  
  4743.                             Source Code Clarification
  4744.  
  4745.        Many of the conventions used by WASM are also used by other
  4746.        assemblers and debuggers.  This section compares WASM to other
  4747.        assemblers and the DEBUG program provided with DOS.  This section
  4748.        also points out a few particulars of WASM syntax.
  4749.  
  4750.        Some assemblers add a suffix to the mnemonic to indicate the size
  4751.        of the operation, whether immediate data is involved, and the type
  4752.        of calls, jumps, and returns that are being used.  WASM identifies
  4753.        the type and size of the instruction mainly on the basis of the
  4754.        operands, in accordance with the DOS DEBUG program.
  4755.  
  4756.        WASM allows the programmer to define the size of the operand
  4757.        through the use of a functional operand (BYTE, WORD, etc.).  This
  4758.        is very similar to the structure used by the DEBUG program and the
  4759.        IBM Macro Assembler.
  4760.  
  4761.          ;the following statement in WASM...
  4762.           Mov WOrD [5+sI+  10 +Bp+5], not 1111111111111111B
  4763.  
  4764.          ; ...is disassembled as the following in DEBUG
  4765.          ; MOV     W,[BP+SI+14],0000          ;DOS 1.1 DEBUG
  4766.          ; MOV     WORD PTR [BP+SI+14],0000   ;DOS 2.0 DEBUG
  4767.  
  4768.        Near and far indirect branching may be implemented by specifying
  4769.        the size of the operand or actually using the NEAR and FAR
  4770.        functions.  Debug uses FAR for far branching and nothing for near
  4771.        branching.
  4772.  
  4773.           Call Near [Bx]  ;
  4774.           Call Word [Bx]  ;these two are the same thing to WASM
  4775.          ;Call [Bx]       ;debug format
  4776.  
  4777.           Call Far [Bx]    ;
  4778.           Call Dword [Bx]  ;these two are the same thing to WASM
  4779.          ;Call Far [Bx]    ;debug format
  4780.  
  4781.        The size of the string manipulation instructions are specified by
  4782.        a B or W suffix added to the mnemonic.  This is the same as the
  4783.        DEBUG program.
  4784.  
  4785.           Movsb  ;move string byte
  4786.           Movsw  ;move string word
  4787.  
  4788.        JMPS is the mnemonic that WASM uses to specify a short
  4789.        unconditional jump to a near label.  JMP always means a long jump.
  4790.        The (DOS 2.0) DEBUG program uses JMP for both long and short
  4791.        jumps.
  4792.  
  4793.           Jmps Location1    ;short unconditional jump
  4794.           Jmp Location1     ;long unconditional jump
  4795.  
  4796.  
  4797.        100                                      Source Code Clarification
  4798.  
  4799.        WASM sets the type of return for a RET based on the procedure
  4800.        type.  A near (within segment) or far (intersegment) return may be
  4801.        encoded without using a PROC through the use of RETN and RETF
  4802.        respectively.  The DEBUG program uses RET to indicate a near
  4803.        return and a RETF to indicate a far return.
  4804.  
  4805.           Proc  Far               ;<---
  4806.           Ret         ;far return     ; far routine
  4807.           Retn        ;near return    ;
  4808.           Retf        ;far return     ;
  4809.                                       ;
  4810.           Proc  Near                  ; <---
  4811.           Ret         ;near return    ;    ; near routine
  4812.           Retn        ;near return    ;    ;
  4813.           Retf        ;far return     ;    ;
  4814.           Endp                        ; <---
  4815.                                       ;
  4816.           Ret         ;far return     ;
  4817.           Endp                    ;<---
  4818.  
  4819.        The bit shifting instructions (SHL, SHR, ROL, etc.) are
  4820.        interpreted to be a single shift by WASM if there is only one
  4821.        operand (the operand to be shifted).  Shifts using the CL register
  4822.        as a counter are implemented by specifying CL as the second
  4823.        operand.  The DEBUG program requires a "1" as a second operand to
  4824.        specify a single shift.
  4825.  
  4826.            Rol Ax      ;roll AX left by one
  4827.          ; Rol Ax,1    ;roll AX left by one, DEBUG format
  4828.            Shr Byte [Bx],Cl   ;shift 8 bits at [BX] CL times
  4829.  
  4830.        Some assemblers leave out an operand if the operand is implicit in
  4831.        the instruction.  AX is implicit in the following 8086
  4832.        instructions: IN, OUT, MUL, IMUL, DIV, and IDIV.  WASM requires
  4833.        the AX (or AL) register in the IN and OUT instructions but allows
  4834.        the others with or without it.  The DEBUG program leaves out the
  4835.        AX or AL register on multiply or divide instructions, but does not
  4836.        on the others.
  4837.  
  4838.           In    Ax,Dx   ;AX receives input word from port in DX
  4839.  
  4840.          ;both of the following are: AX = DX.AX x CX
  4841.           Mul   Ax,Cx   ;WASM allows this
  4842.           Mul   Cx      ;WASM and DEBUG allow this
  4843.  
  4844.        DEBUG assembles some 8087 instructions differently than WASM.
  4845.  
  4846.           Fadd St(1)           ;this in WASM is encodes to
  4847.           Fadd St, St(1)       ;<--- this
  4848.  
  4849.           Fadd St(1)           ;but this in DEBUG encodes to
  4850.           Fadd St(1), ST       ;<--- this
  4851.  
  4852.  
  4853.        Source Code Clarification                                      101
  4854.  
  4855.        WASM and DEBUG implement instruction prefixes as a separate
  4856.        instruction, i.e. they appear on the line above the instruction to
  4857.        modify.  The prefixes are: LOCK, REP, REPE, REPNE, REPNZ, REPZ,
  4858.        and SEG.
  4859.  
  4860.           Rep
  4861.           Stosb       ;store byte CX times
  4862.  
  4863.           Seg Ss
  4864.           Mov Ax,[Bx] ;[Bx] is in the stack segment (SS)
  4865.  
  4866.        Individual segment overrides may also be specified as CS:, DS:,
  4867.        ES:, and SS:, which is how segment overrides are implemented by
  4868.        DEBUG.
  4869.  
  4870.          ;this is assembled properly by WASM and DEBUG
  4871.           Cs:           ;to WASM, this is the same as SEG CS
  4872.           Mov [500], Dl  ;[500] is in the code segment (CS)
  4873.  
  4874.        WASM and DEBUG both specify indirect memory operands by putting
  4875.        all values and registers inside the brackets.
  4876.  
  4877.          ;this in WASM ...
  4878.            Sub [Bx+10],Ax
  4879.            Sub [BX+Data],Ax
  4880.          ;... may be implemented by others like one of these
  4881.          ; Sub [Bx]+10,Ax
  4882.          ; Sub 10[Bx],Ax
  4883.          ; Sub Data[Bx],Ax
  4884.  
  4885.          Data Label Word
  4886.  
  4887.        The mnemonic for an optimized type 3 interrupt is INT3.
  4888.  
  4889.          ;both of statements these cause type 3 interrupts,
  4890.          ;but the first uses only one byte of code
  4891.           Int3
  4892.           Int 3
  4893.  
  4894.        WASM assumes the entire program and all data are in the same
  4895.        segment, so there are no segment definitions.  The location
  4896.        counter is automatically started at 100H, in accordance with COM
  4897.        file format.  Though WASM doesn't allow segment definitions, a
  4898.        program may, of course, set up and maintain its own segments
  4899.        during execution.
  4900.  
  4901.        The implementation and usage of assembly directives vary among
  4902.        assemblers.  The general format of procedure, macro, and data
  4903.        declarations are similar, but mostly incompatible among
  4904.        assemblers.  WASM uses a fairly simplified set of directives, most
  4905.        of which are comparable, though not compatible, to other
  4906.        assemblers.
  4907.  
  4908.  
  4909.        102                                      Source Code Clarification
  4910.  
  4911.        Several 8086 instructions mean the same thing as other
  4912.        instructions and produce identical object code.  The DEBUG program
  4913.        always disassembles these instructions using one particular
  4914.        mnemonic.  One example is JNLE (jump not less or equal) and JG
  4915.        (jump greater).  The DEBUG program disassembles both of these
  4916.        instructions as JG.
  4917.  
  4918.        Symbols that are declared within skipped source code should be
  4919.        undefined.  These symbols, though, are placed in the symbol table
  4920.        anyway and still subject to duplicate definition and other symbol
  4921.        declaration errors.
  4922.  
  4923.          ;in theory the second two symbols don't really
  4924.          ;exist, since they are in source code that is
  4925.          ;skipped because of the false IF directive; in
  4926.          ;spite of "not existing," the second declaration
  4927.          ;of SYMBOL2 causes a duplicate definition
  4928.  
  4929.          Symbol2
  4930.           If 0
  4931.          Symbol1  ;considered undefined
  4932.          Symbol2  ;duplicate definition
  4933.           Endif
  4934.  
  4935.        There is an uncaught error for certain registers as operands.
  4936.        When the operand DX is used in IN's and OUT's, and CL is used for
  4937.        shifts and rolls, WASM only looks for a register type, not those
  4938.        particular registers.  This means that in those cases any register
  4939.        will work in place of a DX or CL (except a segment register).
  4940.        Also WASM does not search for extra operands, they do not cause
  4941.        errors if they exist.
  4942.  
  4943.          ;some uncaught errors
  4944.           In  Ax,Bx
  4945.           Shl Ax,Bx
  4946.           Mov Ax,Bx,Cx,Dx
  4947.  
  4948.  
  4949.        Memory Limitations                                             103
  4950.  
  4951.                                Memory Limitations
  4952.  
  4953.        WASM requires a about 100 kilobytes (K) of free RAM for execution.
  4954.        The only aspect of WASM that varies with the amount of available
  4955.        memory is the macro storage capacity.  With a minimum amount of
  4956.        memory (100K), less than a 1000 bytes of macro storage is
  4957.        available.  Every free byte after that, up to 64K, is used for
  4958.        macro storage.  With 164K bytes available, the maximum usable
  4959.        amount of memory, about 1600 lines at 40 characters apiece can be
  4960.        stored.  The length of the macro lines is significant, i.e. the
  4961.        shorter the lines, the more lines that can be stored.
  4962.  
  4963.        The symbol table has room for about 2000 symbols at 10 bytes
  4964.        apiece.  Like macro lines, the shorter the symbols, the more
  4965.        symbols that can be stored.  An internal code table (which saves a
  4966.        partial tokenized assembly of the program) has room for 10800
  4967.        entries.  Every source line creates an entry in the code table,
  4968.        except blank lines and lines resulting from a macro expansion.
  4969.        Lines that are skipped due to conditional assembly and the
  4970.        conditional directives themselves DO take up room in the code
  4971.        table, even though they do not show up in the assembly.  The
  4972.        symbol table size and code table size do not change, even if the
  4973.        memory is available.
  4974.  
  4975.  
  4976.        104                                                   Bibliography
  4977.  
  4978.                                   Bibliography
  4979.  
  4980.        These books were used as references in the development of WASM and
  4981.        the writing of this documentation.  In addition to this list,
  4982.        there are many other excellent sources of information on the
  4983.        8086/8088 microprocessor and assembly language programming.
  4984.  
  4985.        Angermeyer, John, and Kevin Jaeger. "MS-DOS Developer's Guide."
  4986.          Indianapolis, IN: Howard W. Sams & Co., 1986.
  4987.  
  4988.        "BASIC Version 1.10." 2st ed. Boca Raton, FL: International
  4989.          Business Machines Corp., 1981 and 1982.
  4990.  
  4991.        Duncan, Ray. "Advanced MS DOS." Redmond, WA: Microsoft Press,
  4992.          1986.
  4993.  
  4994.        "iAPX 86/88, 186/188 User's Manual." Santa Clara, CA: Intel
  4995.          Corp., 1985.
  4996.  
  4997.        King, Richard A. "The IBM PC-DOS Handbook." Berkeley, CA: SYBEX
  4998.          Inc., 1983.
  4999.  
  5000.        Morgan, Christopher L., and Mitchell Waite. "8086/8088 16-Bit
  5001.          Microprocessor Primer."  Peterborough, NH: BYTE/McGraw-Hill,
  5002.          1982.
  5003.  
  5004.        "Technical Reference." Rev. ed. Boca Raton, FL: International
  5005.          Business Machines Corp., 1981, 1982, 1983, and 1984.
  5006.  
  5007.        "Turbo Pascal Reference Manual Version 3.0." Scotts Valley, CA:
  5008.          Borland International Inc., 1983, 1984, and 1985.
  5009.  
  5010.  
  5011.        Index                                                          105
  5012.  
  5013.                                       Index
  5014.  
  5015.        $                           61      Declaring data (cont.),
  5016.        '                           11        examples                  36
  5017.        ()                          14        location                  35
  5018.        ,                            6        storage                   35
  5019.        ;                            7        string                    35
  5020.        ?                           11        word                      35
  5021.        []                          11      Default file name            4
  5022.        8087,                       97      Delimiter                    6
  5023.          stack                     11      Directive,               6, 37
  5024.        Addressing,                           compatibility            101
  5025.          direct                    11        conditional               19
  5026.          indirect                  11        list of                   80
  5027.          registers                 11        syntax                     9
  5028.        ANYSIZE function            55      Distribution policy          1
  5029.        ASM filename extension       4      Dollar sign                 61
  5030.        Assembling programs          4      DS directive            35, 38
  5031.        BASIC subroutines           98      DW directive            35, 38
  5032.        Basic syntax                 6      DWORD function          56, 99
  5033.        Blank line                   7      EDLIN program                6
  5034.        Bload,                              $END constant               62
  5035.          address                   98      ELSE directive  19, 20, 21, 38
  5036.          format                    98      ELSEIF directive    19, 20, 21
  5037.        Brackets                    11                                  39
  5038.        Bug, in WASM               102      End of file                  6
  5039.        BYTE function           55, 99      ENDIF directive     19, 21, 39
  5040.        CALL instruction            17      ENDM directive          28, 40
  5041.        $CHKSUM constant            61      ENDP directive          17, 40
  5042.        COM filename extension       4      EQU directive               40
  5043.        Comma                        6      Equates                      8
  5044.        Comment,                            Error,                   5, 69
  5045.          description of messages   70        AND                       14
  5046.          message                   69        count                     69
  5047.          source                     7        critical                  69
  5048.        Compatibility of                      description of messages   70
  5049.          source code               99        flagging                  69
  5050.        CON device                   4        macro                     34
  5051.        Conditional assembly,       18        message                   69
  5052.          directive                 19        MOD                       14
  5053.          nested                    22        multiple                  69
  5054.          operand                   19        OR                        14
  5055.          operand testing           25        XOR                       14
  5056.          operator                  24      Error code,
  5057.        Constant                    61        upon termination           5
  5058.        Control characters           6      ERROR directive         41, 69
  5059.        $COUNT constant             61      ERRORLEVEL
  5060.        Data declaration            35        batch command              5
  5061.        $DATE1 constant             62      ERRORMAX directive      42, 69
  5062.        $DATE2 constant             62      EXPAND+ directive   34, 42, 66
  5063.        DB directive            35, 37      EXPAND- directive   34, 42, 66
  5064.        DEBUG program               99      Expression,                 14
  5065.        Declaring data,             35        examples                  14
  5066.          byte                      35        operators                 14
  5067.  
  5068.  
  5069.        106                                                          Index
  5070.  
  5071.        Expression (cont.),                 Macro (cont.),
  5072.          signed                    14        nested                    32
  5073.        File name, default           4        parameter             28, 30
  5074.        FLAGALL+ directive      43, 69        recursive                 32
  5075.        FLAGALL- directive      43, 69        symbol                    28
  5076.        IF directive    19, 21, 22, 43      MACRO directive         28, 47
  5077.        IFN directive   19, 21, 22, 43      MACROC directive        33, 47
  5078.        Immediate data,             10      Memory operand,             11
  5079.          characters                10        addressing registers      11
  5080.          in expressions            14        direct addressing         11
  5081.          size                      12        indirect addressing       11
  5082.        INCLUDE directive           44        size                      12
  5083.        Instruction,          6, 9, 37      Memory,
  5084.          bit shifting             100        allocation                62
  5085.          disassembly              102        code table               103
  5086.          list of                   80        label                      8
  5087.          prefix and override      101        limitation               103
  5088.          string                    99        minimum                  103
  5089.          syntax                     6        segments                 101
  5090.        Interrupt, type 3           98        symbol table             103
  5091.        JMP instruction             99      Message,
  5092.        JUMP+ directive         44, 69        descriptions              70
  5093.        JUMP- directive         44, 69        during assembly           69
  5094.        Label,                       8      NEAR function           56, 99
  5095.          in expressions            14      NEG function                57
  5096.          memory                 8, 35      NEXTIF directive    19, 21, 48
  5097.          near                       8      NOT function                57
  5098.        LABEL directive         35, 45      Number,                     10
  5099.        Line,                                 binary                    10
  5100.          blank                      7        decimal                   10
  5101.          syntax                     6        hexadecimal               10
  5102.        LINESIZE directive          46        signed                    10
  5103.        List,                    4, 66        size                      12
  5104.          columnar headings         67      Object file                  4
  5105.          header                    66      OFFSET function             58
  5106.          line                      67      Operand,                 6, 10
  5107.          page number               66        conditional               19
  5108.          paging                    66        constants                 61
  5109.          subtitle                  66        examples                  12
  5110.          symbol table              68        expressions               14
  5111.          title                     66        functional                55
  5112.        List file                    4        implicit                 100
  5113.        LIST+ directive         46, 66        required                  10
  5114.        LIST- directive         46, 66        size                  11, 25
  5115.        $LOC constant               63        syntax                     6
  5116.        LST filename extension       4        type                  10, 25
  5117.        Macro,                   8, 27        value                     25
  5118.          conditional               33      Operator,                   14
  5119.          defining                  28        conditional               24
  5120.          error                     34      ORG directive               49
  5121.          in conditional code       30      Origin,                     49
  5122.          invocation                30        default                  101
  5123.          listing                   34      Page number                 66
  5124.          memory limitation        103      PAGE+ directive         50, 66
  5125.  
  5126.  
  5127.        Index                                                          107
  5128.  
  5129.        PAGE- directive         50, 66      Subroutine (cont.),
  5130.        PAGESIZE directive      50, 66        Pascal                    98
  5131.        Parameter,                            relocation                98
  5132.          command line               4      SUBTITLE directive      52, 66
  5133.          command line examples      5      Symbol,                   6, 8
  5134.          macro                     28        as instructions            8
  5135.          macro                     30        as operands                8
  5136.          procedural                17        declaration                8
  5137.        Parenthesis,                14        declaration syntax         6
  5138.          signed                    14        label                      8
  5139.        Pascal subroutines          98        location of declaration    8
  5140.        Printer                      4        macro                     28
  5141.        PRN device                   4        required declaration       6
  5142.        PROC directive          17, 51        reserved                  65
  5143.        Procedure,                  17        table                      8
  5144.          declaration               17        type                       8
  5145.          far                       17        type determination         8
  5146.          local data                17        undefined                102
  5147.          near                      17        uniqueness        8, 65, 102
  5148.          nested                    17      Symbol table,                8
  5149.        Program structure           16        list                      68
  5150.        Question mark               11        memory limitation        103
  5151.        Quotation mark              11      SYMDUMP+ directive  52, 66, 68
  5152.        QWORD function              58      SYMDUMP- directive          52
  5153.        Register,                   10      System requirements          2
  5154.          16 bit                    11      TBYTE function              59
  5155.          8 bit                     10      Termination of assembly     69
  5156.          segment                   11      $TIME1 constant             63
  5157.          size                      12      $TIME2 constant             63
  5158.        Registration                 1      TITLE directive         53, 66
  5159.        RESETC directive            51      True                        24
  5160.        RET instruction        17, 100      TYPE function               59
  5161.        Semi-colon                   7      UNUSED+ directive       53, 69
  5162.        SIZE function               58      UNUSED- directive       53, 69
  5163.        $SIZE constant              63      VALUE function              59
  5164.        $SUM constant               63      $VERSION constant           64
  5165.        Source code,                        WORD function           59, 99
  5166.          clarification             99
  5167.          compatibility             99
  5168.          external                  44
  5169.        Source file,                 4
  5170.          external                  44
  5171.          type                       6
  5172.        Spaces                       6
  5173.        ST operand                  11
  5174.        Statistics, assembly         5
  5175.        String,                     11
  5176.          declaration               35
  5177.        Structured programing       16
  5178.        Subroutine,                 98
  5179.          BASIC                     98
  5180.          debugging                 98
  5181.          location counter          98
  5182.          naming                    98
  5183.  
  5184.  
  5185.